レガシーコードからの脱却

https://www.oreilly.co.jp/books/9784873118864/
レガシーを改善したい、そんな想いからこの本を手にとった・・・!
事前インプット
第1部 レガシーコード危機
1章 何かが間違っている
レガシーコードが生まれる要因を書いている章。レガシーコードにならないように防ぐ方法や保守の仕方についても知る必要がある。また従来のウォーターフォールのように機能をまとめて作るのはレガシーコードを作り出す可能性が高い。
マイケル・フェザーズは、テストがないコードがレガシーコードと定義している。
- メモ
- コードモンキー(アーキテクチャーは設計のことを考えずにただコードだけを書く人のこと)
2章 CHAOS レポート再考
- CHAOS レポート
- 成功: 当初指定した機能を納期通りに完成し、予算内に収める
- 問題あり: 予算を超過した、または納期に間に合わなかった、もしくはスコープを削った
- 失敗: キャンセルされたPJ
CHAOS レポート自体に疑問はあるが、ソフトウェア開発が非効率になっていてビジネスに巨大な損失がもたらされていることに間違いはないため、改善に向けて取り組んでいかなければいけないよね、という話
3章 賢人による新しいアイデア
- アジャイルに入門する
- リーン
- XP(エクストリームプログラミング)
- スクラム
- バッチは小さいほどよい
アジャイルの利点は開発をディスカバリープロセスにできることだ。アジャイルでいうところのストーリーは、それ自体がウォーターフォールでもとめられるような冗長で詳細な仕様書と置き換えが可能なものではない。ストーリーは会話のきっかけとなるものでなければいけない。ソフトウェア開発者とプロダクトオーナーとのあいだの有意義な対話を必要とし促すのだ。
スクラムは自己組織化を促すものだが、それだけでコードの品質に焦点をあて保守可能なソフトウェアをつくるのに役立つようなプラクティスを採用しよう、となるわけではない。
キーワードとしてアジャイル、技術的卓越性などがあった。保守しやすいコードを作るためのプラクティスを常に取り入れながらイテレーティブに改善していくということが大事。これまで自分はアジャイルを技術的な観点であまりみておらず、プロダクトに重点を置いていた。アジャイル宣言の背後にある原則の中の 技術的卓越性と優れた設計に対する不断の注意が機敏さを高めます。
というところにフォーカスをしていくことがレガシーコードを作らないようにする第一歩であることを認識した。
第2部 ソフトウェアの寿命を伸ばし価値を高める9つのプラクティス
4章 9つのプラクティス
- やり方より先に目的、理由、誰のためかを伝える
- 小さなバッチで作る
- 継続的に統合する
- 協力しあう
- 「CLEAN」コードを作る
- まずテストを書く
- テストでふるまいを明示する
- 設計は最後に行う
- レガシーコードをリファクタリングすす
5章 プラクティス1 やり方より先に目的、理由、誰のためかを伝える
レガシーコードを改善していく話ではなかった。スクラムにおけるストーリーにおいてやり方の前に目的、理由、誰のためのものなのかをわかりやすくしようという話だった。レガシーコードを見る前に今の開発プロセスを見つめながら、やり方を検討する、ただ作るということになっていないかを見直す必要があって、レガシーコードが作られないようなプロセスにしていくことが大事という話。
またその中でプロダクトオーナーが依存性を取り除いたりリファクタリングを後押ししたりすることでバランスをみながらレガシーコードにならないようにしていくことも必要。
6章 プラクティス2 小さなバッチで作る
小さく早く作りフィードバックをもらうことの大事さを書いている。また顧客にとって価値があるものにもとづいて開発のメトリクスを計測することも必要。
- 計測の実践
- 価値実現までの時間の計測
- コーディングに使った時間の計測
- 欠陥密度の計測
- 欠陥検出までの時間の計測
- 機能ごとの顧客価値の計測
- 機能を提供しない場合のコストの計測
- フィードバックループの効率の計測
開発プロセスめっちゃ大事やん
プラクティス1, 2 はレガシーコードをどうこうする話ではなく、開発プロセスをいかに改善することが大切かということだった。1,2 にこれらが来ているということは、いきなりコードをみるのではなく、レガシーコードになってしまった原因やプロセスの改善ポイントを探しまずそこから改善していくのがよい、ということだと思った。コードの設計手法やモデリングも大事だけど、その前のチームで開発する際のプロセスがそれらの基盤として支えるということが認識できた。開発プロセスめっちゃ大事やん。
7章 プラクティス3 継続的に統合する
統合 = インテグレーション(integration) なので継続的インテグレーションは大事だよって話。
- 完了
- 自分のマシンで動くこと
- 完了の完了
- 自分のマシンで機能し、ビルドにも統合されている
- 完了の完了の完了
- 自分のマシンで機能し、ビルドにも統合され、クリーンで保守可能になっている状態
継続的に統合し、ストーリーを完了の完了の完了になるまで終わりにしない。そのためにビルドやデプロイを可能な限り自動化しましょう。このあたりは大多数の開発の現場で普通にやっていることな気がするので、そうだよね〜という感じ。ただ、もしCIやCDが自動化されてない現場だったとしたら安心して開発できる気がまったくしないので、重要なことであると思った。
8章 プラクティス4 協力しあう
協業も大事でスキルの一つで、チームの本当の一員にならなければいけない。エクストリームプログラミングも協業から始まったプラクティス。
ペアプログラミング
- XPのプラクティスのうちもっとも価値がある
- チームに知識を広げるもっとも速い方法
- 設計・デバッグの時間短縮、保守性向上のためのコードの掃除にも有効
- コードの美的感覚の共有
- 対等な人同士の協業関係
- ペアプログラミングによって失われるプログラマーの時間は15%
- 割り込みが減る、2人で作業していると周りは割り込みにくくなる
- 学びや成果から満足度は高まる
バディプログラミング
- 全時間ではなく1時間のみとかでコードをレビューする
- バディはランダムに交代する
レトロスペクティブ
- 小さな改善を探す
- プロセスを責めよ、人を責めるな
- なぜなぜ5回をやってみる
- 根本原因に取り組む
- 全員の意見を聞く
- 人に権限を
- 進捗を測ること
9章 プラクティス5 「CLEAN」コードを作る
- Cohesive (凝集性)
- それぞれの部品(クラスやメソッドなど)は1つのものだけを扱う
- 名前をつけるのが難しければ責任がうまく定義できていない
- コンポジション
- Loosely Coupled (疎結合)
- 間接的にしか依存しない
- Encapsulated (カプセル化)
- Assertive (断定的)
- 自分自身の責任は自分で管理しわかりやすくなっている
- Nonredundant (非冗長)
- 意図しない冗長性
明日のベロシティを上げるには今日コード品質あげることだ
技術的負債は、開発中に学習した内容をコードに反映しなかったときに起こるもの
耳が痛い。。
10章 プラクティス6 まずテストを書く
- 最初にテストを書くテスト駆動開発
- リファクタリングをサポートしてくれる
- テスト可能なコードを書く
11章 プラクティス7 テストでふるまいを明示する
- テストは仕様
- 全てのバグはテストがない故に存在する
- 実装ではなくふるまいをテストする
- テストはセーフティネット、心理的な保証を作ってくれる
12章 プラクティス8 設計は最後に行う
- テストを先に書いたのでその後設計する
- 死んだコードを消す
- 名前を変更する
- コードは書くより読む方が多い
13章 プラクティス9 レガシーコードをリファクタリングする
- 良い習慣を身につけるためにリファクタリングする
- エキサイティングでチャレンジング
- ピンニングテスト
- ストラングラーパターン
- オープンクローズドにリファクタリングする