にわかプラス

にわかが玄人になることを夢見るサイトです。社会や国際のトレンド、プログラミングや電子工作のことについて勉強していきたいです。

ドメイン駆動設計入門 は設計の軸足になるべき本

sponsor

「ドメイン駆動設計入門 ボトムアップでわかる! ドメイン駆動設計の基本」 を読んだ。

設計の本を探すと、必ず話題に登場するのが、エリック・エヴァンスのドメイン駆動設計。 今までに何度も読もうとしたけれど、難しいという評判を聞いて手が出せずにいた。

2020年4月に発売された、ドメイン駆動設計入門の本がわかりやすいと聞いたので、こちらを読んでみることにした。 なんでも、原書は前提となる知識がある状態で書かれているらしく、本書はその部分を補って書いてくれているのだという。

結論から言って、めちゃくちゃわかりやすいいい本だった。
期待していたとおり、前提知識は丁寧に解説されていた。さらに、解説文に必ずコード例があるため、実装のイメージも湧きやすく、そのまま設計に活かせる内容だった。

ドメイン駆動設計入門 ボトムアップでわかる! ドメイン駆動設計の基本

ドメイン駆動設計入門 ボトムアップでわかる! ドメイン駆動設計の基本

  • 作者:成瀬 允宣
  • 発売日: 2020/02/13
  • メディア: 単行本(ソフトカバー)

目次

Chapter1~10が個別の話で、索引的に使うと良さそう。
Chapter11~13は今までの話を用いて1つのアプリケーションを作る実践例となっていて、実装を追体験できる。

Chapter1. ドメイン駆動設計とは
Chapter2. システム固有の値を表現する「値オブジェクト」
Chapter3. ライフサイクルのあるオブジェクト「エンティティ」
Chapter4. 不自然さを解消する「ドメインサービス」
Chapter5. データにまつわる処理を分離する「リポジトリ」
Chapter6. ユースケースを実現する「アプリケーションサービス」
Chapter7. 柔軟性をもたらす依存関係へのコントロール
Chapter8. ソフトウェアシステムを組み立てる
Chapter9. 複雑な生成処理を行う「ファクトリ」
Chapter10. データの整合性を保つ
Chapter11. アプリケーションを1から組み立てる
Chapter12. ドメインのルールを守る「集約」
Chapter13. 複雑な条件を表現する「仕様」
Chapter14. アーキテクチャ
Chapter15. ドメイン駆動設計の扉を開こう

Chapter1~10

ドメインという考え方の必要性、その実装方法ついて本書の半分以上をさいて解説してある。
とても内容が盛りだくさんだが、細かく章で切ってあるのでとても読みやすい構成だった。

ドメインは対象のとなる問題を抽象化してモデル化したもの。
そのモデルの固有の値を表すのが「値オブジェクト」「エンティティ」
上記モデルで表しきれない固有の値に対するルールを定義する「ドメインサービス」
保持し続ける部分が「リポジトリ」
対象となる問題を解決する処理が「アプリケーションサービス」

このような構成で設計していく。

Chapter11~13をクラス図にしてみた

Chapter11~13では今までに説明してきたドメイン駆動設計とその実装を元に、サークルを設計する。

サークルは、大学などでよく見るあのサークル。

役割は以下。

  • サークルを作成する
  • サークルに参加する
  • サークルに勧誘する

本書の最後で、これらは「レイヤードアーキテクチャ」を意識して作っているという記述があった。
そこで、このサークルの設計をレイヤードアーキテクチャを意識してUMLのクラス図に起こしてみた。

レイヤードアーキテクチャを構成する4つの層の内訳は以下の通り。

  • プレゼンテーション層(ユーザインタフェース層)
  • アプリケーション層
  • ドメイン層
  • インフラストラクチャ層

今回プレゼンテーション層の記載はないので、残りの3層に分類するように作図した。

クラス図

使用したツールはDraw.io。グラフィカルで簡単に作図できた。
VS Codeのエクステンションを使って書いたが、普通にWebでも書ける。環境を選ばないというのは素晴らしい。

アプリケーション層

  • CircleapplicationService:サークルの役割を行うアプリケーション部分

ドメイン層

  • 値オブジェクト
    • CircleID:サークルIDを表す
    • CircleName:サークルの名前をあらあわす
    • User:ユーザのオーナを表す
  • エンティティ
    • Circle:サークルを表すエンティティ
  • ドメインサービス
    • CircleService:サークルの重複確認をおこなう
  • コマンド
    • CircleCreateCommand:サークル作成処理のコマンド
    • CircleJoinCommand:サークル参加処理のコマンド
  • 仕様
    • CircleFullSpecification:サークルが満員かどうかを判断する
    • CircleRecommendedSpecification: オススメサークルかどうかを見極める仕様
  • 他の層とのインタフェース
    • ICircleRepository:インフラ層のサークルデータを永続化するための機能へのインタフェース
    • IUserRepository:インフラ層のユーザデータを永続化するための機能へのインタフェース
    • IUserNotification:UserDataModelでのやり取りをするための機能へのインタフェース

インフラ層

  • CircleRepository:SQLでのやり取りをする機能
  • EFUerRepository:UserDataModelでのやり取りをする機能

その他

  • ICircleFactory : Circleを生成するためのファクトリクラス
  • UserDataModelBuilder:UserDataModelを生成する

f:id:hiddenvally333:20200714215219p:plain
サークルモデルのクラス図

ドメイン層インフラ層のやり取りはインタフェースを介して行っていることがわかる。

インフラ層Repositoryが、SQLや内蔵ROMに変わったりとすることが予想されるから、柔軟性をもたせている。

アプリケーション層ドメイン層はインタフェースを介さない。

おそらく、アプリケーション層からアクセスしたいドメイン層のオブジェクトが多すぎて、インタフェースを作成すると逆に複雑になってしまう恐れがある。

その代わり、同じような処理のバリエーション違いを実現させたいときは、Command仕様といったオブジェクトを挿し替えることにより、柔軟性を持たせている。

おわりに

クラス図に起こしてみると各クラスの依存がわかりやすくなって、頭の整理になった。
クラス図はもっと機能を絞ってを書くべきという気もしたけれど、今回は全体を俯瞰するという意味ではとても良かったかな。

本書は基本的なところから実装まで一気通貫で解説してくれていてとても良かった。 これから設計をするときはこの本を軸足にやっていこうと思う。

ドメイン駆動設計入門 ボトムアップでわかる! ドメイン駆動設計の基本

ドメイン駆動設計入門 ボトムアップでわかる! ドメイン駆動設計の基本

  • 作者:成瀬 允宣
  • 発売日: 2020/02/13
  • メディア: 単行本(ソフトカバー)