レガシーコードにおいて悪者とされるコードの依存について
修正するのが怖くて危険になってしまったようなレガシーコードを改善する文脈では、依存が悪者として扱われることが多いです。しかし、特にフレームワークやライブラリを使ってプログラムを書く以上、フレームワークやライブラリの機能を使うので、依存することは避けられません。ということは、依存が悪という単純な解像度の理解では十分ではなくて、自分で書くコードが何に依存しているかを把握し、依存をコントロールすることが肝要ということです。
コントローラーは、フレームワークの提供する親クラスを継承して作ることが多いです。Laravelを例として、コントローラーに記述した、とあるRoute
に関連付けられたメソッドが何に依存する可能性があるかをリストアップしてみます。
- 引数で受けとった
Request
オブジェクトを参照する - 親クラスのフィールドを参照/更新する
- 親クラスのメソッドを呼び出す
Middleware
ミドルウェアの処理結果を前提とした処理を行なう- Laravelのファサードを呼び出す
DB
、Auth
、Cookie
、Session
…
- Laravelの提供するグローバル関数を使用する
response()
、view()
beforeFilter
に登録したメソッドの処理結果を前提として処理を行なうModel
クラスを呼び出す- 自作したプライベートメソッドを呼び出す
- 自分で定義したフィールド編集を参照/更新する
依存する可能性のある対象が多いということは、一概に良くないということを主張したいのではありません。便利で親切なフレームワークであればあるだけ、その裏返しとして多数の依存先が存在します。
コントローラーのメソッドにコードを記述するということは、カジュアルに無意識にこれらの対象に依存するということです。言い替えると、元のコントローラーのメソッドのコードを一切変更しなくても、これらの対象の動作の変更や修正の影響を受ける可能性があるということになります。
なにも意識せずに機能を実装した場合、コントローラーに、多数の依存先に絡まった状態でビジネスロジックが記述されます。多数の依存先の修正の影響を受けやすい事に加えて、自動テストを書くことも非常に困難な状態となってしまいます。
このような状態になったレガシープロジェクトを改善するために何ができるかというと、ビジネスロジックが何に依存しているかを明確にし、可能であれば依存しないプログラム構造に変更し、自動テストで守られた安定したクラス郡として、ビジネスロジックを隔離することが有効です。この対策のサンプルプログラムを使った具体的な説明については、「ドメインを純粋に保つ」というテーマで書いていますので、是非読んでみてください。