little hands' lab

ドメイン駆動設計、アジャイルプラクティスを実践し、解説しています。

ドメイン駆動設計で実装を始めるのに一番とっつきやすいアーキテクチャは何か[DDD]

DDD連載記事

背景・前提

なぜDDD初心者はググリ出してすぐに心がくじけてしまうのかの記事で、

ネット上の文献で紹介されるアーキテクチャが様々なものとなっているのです。IDDDではヘキサゴナルアーキテクチャというものが掲げられていましたが、それを進化させたオニオンアーキテクチャ、クリーンアーキテクチャなどの有名な亜種が存在します。 これが実装に着手する際に非常に大きな混乱を呼ぶのです。文脈の理解、採用するアーキテクチャの選定に時間を取られることでしょう。

と書きました。こちらに対して、私が「一番とっつきやすい」と考えるアーキテクチャを紹介します。

前提としてですが、完全に個人的な経験に基づく私見になります。

DDDの理論の中で、アーキテクチャに関しては「エリック・エヴァンスのドメイン駆動開発」(以下原典)と実践ドメイン駆動開発(以下IDDD)とでも異なったものが紹介されており、唯一の正解というものは提示されていません。アーキテクチャは各プロジェクトの判断に委ねられているものであり、合う合わないはプロジェクトの要件やメンバーによって異なります。

ただ、それだけではまず始める時にどう着手すればよいか迷ってしまうと思うので、「初学者が手をつけるならこれが良いのでは」というものを私が提案する形になります。ご了承ください。

候補となるアーキテクチャと、その関係性

ネットでDDDの記事を漁るとだいたい以下のものがでてくると思います。

  1. レイヤードアーキテクチャ
  2. ヘキサゴナルアーキテクチャ
  3. オニオンアーキテクチャ
  4. クリーンアーキテクチャ

これらの概略を簡単にお話しします。

レイヤードアーキテクチャ

Layered.png

原典で紹介されているアーキテクチャ。 従来の3層アーキテクチャに比べて、Domain層を確立させ、そこにドメインロジックを凝集させよう、という発想のものです。

ヘキサゴナルアーキテクチャ

Hexagonal.png

IDDDで紹介されているアーキテクチャ。別名「ポートアンドアダプターアーキテクチャ」。 元はこちらのブログで2005年に提唱されたものです。

実は「ヘキサゴナル、オニオン、クリーン」の3つは、本質的には全く同じです。

思想としてはこのヘキサゴナルで完成されているんですよ。責務の区切り方と名称が少しずつ違うだけなんです。じゃあ、ヘキサゴナルでいいじゃないかって?

そうです、本質的には基本的にヘキサゴナルでよいし、結果的に同じ設計をしていることになるんです。

ただし・・・・

この図を見ても、実装イメージが湧かなくないですか?

私はこれがポイントだと思っていて、このわかりづらさがIDDDを読んだ人が手をすぐ動かせない理由ではないかと考えているのです。

結論を変な位置でいうと、私のオススメはオニオンアーキテクチャです。これは本質的には同じでも、責務の区切りと名称を変えた結果 直感的にわかりやすくなっているので、最初の導入はこの図を見ながらやるのが良いと思っています。

では、次にそちらを紹介します。

オニオンアーキテクチャ

ヘキサゴナルアーキテクチャを受けて、2008年にこちらのブログで提唱されたのがオニオンアーキテクチャです。

Onion.png 同じ構造を、平らに表現したのが以下の図です。 Onion(Flattened).png

少〜し、どういう構造にするのかイメージが湧いてきませんか? 詳細はこの後説明するのですが、ポイントは依存関係逆転の原則によってDomain層がInfrastructure層に依存しなくなっていることです。これによりDomain層のモデルが特定のライブラリなどに依存しない形の実装になるのです。

これはヘキサゴナルアーキテクチャでも全く同じ思想なのですが、概念図からはそのことが読み取りづらいのです。そのため、図を見たときの直感的なわかりやすさから、私は最初に着手するにあたってはオニオンアーキテクチャを推しています。

変な順番になってしまいましたが、比較のためにクリーンアーキテクチャも紹介します。

クリーンアーキテクチャ

ヘキサゴナル、オニオンやその他のアーキテクチャを受けて、2013年に概念を統合しようとしたのがクリーンアーキテクチャです。こちらのブログで提唱されました。

image.png 画像は同ブログから引用

同じく同心円が重なっている構造からわかるように、基本的に言っていることは同じです。違いとしては単語だけだと思っています。

クリーンアーキテクチャは、Androidアプリケーションのアーキテクチャとして、DDDとは関係なく使われている記事がちらほら見受けられました。

これは全くもって好みになるのですが、「UseCase層」というレイヤに何を書くのかわかりにくい点、「Domain層」ではなく「Entity層」というネーミング(DDD的にはEntityはDomain層の一部なので、収まりが悪い)から、私はオニオンアーキテクチャの方がよいと思っています。

これがしっくり来る方はクリーンアーキテクチャのネーミングを採用すれば良いかと思います。

アーキテクチャを使ってどう実装するのか

ドメイン層にどのようにふるまいを詰め込むのか、について、 【DDD】モデルでドメイン知識を表現するとは何か こちらの記事でサンプルコード付きで紹介しています。

Onion(Flattened).png

記事内のTaskエンティティがDomainModel、TaskRepositoryがDomainService、TaskApplicationがApplicationに該当します。 こうして見てみると、結構シンプルですし、レイヤーの名前と内容がイメージしやすいのではないでしょうか。

そういったわけで、私はDDDを最初に説明するときは、オニオンアーキテクチャと先ほどのようなサンプルコードの説明をするところから始めるようにしています。

オニオンアーキテクチャ、依存性の逆転については、また別の記事でもう少し深堀りしてみたいと思います。

(10/11追加)
ドメイン駆動 + オニオンアーキテクチャ概略書きました。

もっと詳しく知りたい方は

little-hands.booth.pm

初めてDDDを学ぶ方、もしくは実際に着手して難しさにぶつかっている方向けの書籍を出しました。
迷子になりがちな「DDDの目的」や「モデル」の解説からはじめ、 具体的なモデリングを行い実装まで落とす事例を元に、DDDの魅力や効果を体感することを目指します。

この本の「第5章 アーキテクチャ」では、本ブログ記事の内容をより詳細に解説してあります。 よろしければお求めください。


また、実践にあたって頻出の疑問に対してトピックごとに詳しく解説した書籍もあります。

重要トピック「モデリング」「集約」「テスト」について詳細に解説し、その他のトピックでは頻出の質問への回答と具体的なサンプルコードをふんだんに盛り込みました。現場で実践して、困っていることがある方はぜひこちらもご覧ください。

little-hands.booth.pm

現場での導入で困ったら

DDDを導入しようとすると結構試行錯誤に時間がかかります。
現場で導入してすぐに効果を発揮したい!!という方向けに、基礎解説とライブモデリング/コーディングを行う勉強会の開催や、設計相談を受付ております。
事例紹介もあるのでご関心あれば覗いてみてください。開催形式は柔軟に対応できるのでお気軽にご相談ください。

little-hand-s.notion.site

Twitterでも、DDDに関して発信したり、「質問箱」というサービスを通じて質問を受け付けています。こちらもよろしければフォローしてください。

https://twitter.com/little_hand_s

また、YouTubeで10分でわかるDDD動画シリーズをアップしています。概要を動画で理解したい方はこちらもどうぞ。チャンネル登録すると新しい動画の通知を受け取ることができます。