コンストラクタか。ファクトリか。

実装に依存せず、全て抽象(インタフェース)に依存するようにするためには、
オブジェクトの生成はコンストラクタではなく、ファクトリで行う必要があります。

ただし、現実問題として全てを抽象(インタフェース)に依存するようなプログラムは、
複雑になりすぎて、保守できるような代物にはならないと思います。

従って、オブジェクトの生成を全てファクトリで行うのではなく、状況に応じてコンストラクタを使い
、プログラムをシンプルにしなければいけないのですが、どのように判断すべきか明確な答えはありません。

この点についてDDDにいくつかアドバイスが紹介されていたのでその内容を記載します。

まずは翻訳書140ページに箇条書きされているコンストラクタが有利に働く状況について転記します。

  • クラスが型(type)である。つまり、興味深い階層の一部ではなく、インタフェースを実装することで多態的に使用されることもない。
  • クライアントが実装に関心がある。おそらくは、ストラテジーを選択する方法として考えているのだろう。
  • オブジェクトの持つ属性をすべてクライアントが取得できるため、クライアントが目にするコンストラクタの内部に、さらに別のオブジェクトの生成がネストされることがない。
  • 構築が複雑ではない。
  • 公開コンストラクタは、ファクトリと同じルールに従わなければならない。すなわち、生成されるオブジェクトの不変条件をすべて満たすアトミックな操作でなければならない。

次に箇条書きにはないが文脈から読み取れる事を記載します。

  • 「銀行口座開設」のようなドメインにとって意味を持つ、オブジェクトの生成であればオブジェクト自身で生成してもよいが、ドメインにとって意味のない(実装のために必要な)オブジェクトの生成はファクトリで生成すべきである。(135ページ)
  • オブジェクトがアクティブなライフタイムの中で決して適用されることのない不変条件のロジックであれば、そのロジックを入れるのに理にかなった場所はファクトリであり、そうすることで生成物はよりシンプルなままに保たれる。(142ページ)

これらを参考に判断すると良いと思います。

エリック・エヴァンスのドメイン駆動設計 (IT Architects’Archive ソフトウェア開発の実践)

エリック・エヴァンスのドメイン駆動設計 (IT Architects’Archive ソフトウェア開発の実践)