はじめに
DDDでの開発をしています。自分も他のメンバーもDDDのプロジェクトはほぼ初です。日々書籍や記事などからDDDについて学びながらの開発です。今回は実際に手探りでプロジェクトでDDDを実践してみて、あまり語られているのを見た事がなく悩んだ問題について書きます。
プロジェクトの状況
- とある企業からの受託開発。
- 発注元の商品そのものというよりは、DDDで言うところのサブドメインにあたる従来システムを0からリプレイス。
- 従来システムは発注元のビジネスの初期から存在し、ビジネスの変化にその場その場のスピード重視で追従することを優先した結果、いまや技術的負債が積み重なり機能追加や改修が困難になっている。
- この反省から新しいシステムには保守性が求められており、DDDを採用。
リプレイスではあるものの、完全に同一の動作をするものを再度作るのではなく、従来のシステムがビジネスの変化に付いていけずに放置され運用で苦労していた部分、今後のビジネスの展望から新しい業務フローに置き換えるべき部分を明らかにしながらアジャイルに開発。
CQRSを採用
問題
開発初期のドメインエキスパートとのミーティングでは聞きなれない言葉が多く出てきます。その中にはかなり曖昧に、不整合に使用されている用語も珍しくはありません。ユビキタス言語が存在しない状態だと、ドメインエキスパートは同じことを異なる言葉で表現したり、違うことを同じ言葉で表現したり、本質とはかけ離れた表現を使います。プログラムとは違い、用語が曖昧なままでも実際のドメインエキスパートの業務に支障はないということでしょう。自身の日常や業務を鑑みても、常に厳密に用語を使っているかというとNoなので納得できます。しかし、システムを開発する上でこれら曖昧な用語は取り除くべき障害です。ドメインエキスパートから発せられる曖昧で不整合な用語に目を光らせながらユビキタス言語として整理していくことが正確なドメイン理解の第一歩と言えるでしょう。ミーティングの中でドメインエキスパートに曖昧で不整合な点を指摘すると大抵の場合「あー言われてみれば確かに」という反応を示して頂け、そこから新たな用語をユビキタス言語として考案していきました。
しばらくはこの調子で順調にやっていたのですが、フロントエンドの開発に取り掛かった段階で問題が発生しました。従来のシステムで曖昧な用語が使われていた部分をユビキタス言語に置き換えて開発したところ、ドメインエキスパートから「そこにはユビキタス言語を使わないで欲しい」と言われました。聞くところによると発注元の社内でだけならまだしも、発注元の顧客からブラウザを通して見える部分にまでユビキタス言語を徹底してしまうと、従来の顧客から分かりにくくなってしまうということでした。また、フロントエンドで開発しようとしていたQueryモデルの項目の中にはCommand側のドメインモデルやユビキタス言語には存在しないものがありました。
対応
今回の案件では保守性を要求されていたため、フロントエンドで使用される用語にもユビキタス言語を使用するべきだと最初考えていました。しかし、ユビキタス言語はあくまでもドメインエキスパートと開発者の間の共通言語で、ユビキタス言語がドメインエキスパートの用語にフィードバックされる訳ではないことに気がつきました。そこで、フロントエンドで使用される用語は基本的にドメインエキスパートの用語を踏襲することにしました。しかしそうなると、フロントエンドで表示されてからUseCaseを実行するまでのどこかでそのミスマッチを解消しなければなりません。そこでControllerからUseCaseを実行する引数を作成する段階でそれらを全て解消することにしました。HTTPリクエストまではドメインエキスパートの用語、UseCaseからはユビキタス言語、それらを変換するのがControllerという形です。
おわりに
DDDを手探りでやっていると思わぬ悩みポイントが発生します。特に今回はDDDをやっていたメンバーがいなかった為「もしかしたらここで妥協すると後々致命的に保守できなくなるのかもしれない」という懸念はありました。しかし、ある程度開発した現段階ではそういったことは起きておらず、むしろフロントエンドが発注元の要望に合わせやすいようになったため、ある意味保守性が上がったと言えます。今回の話題はもしかしたらDDDにより詳しい方からすれば当たり前の話(もしくはより良い方法がある)かもしれませんが、同じことに悩む人の手助けになればいいなと思います。