「ドメイン駆動設計 DDD」のコアナレッジカードのメモ

この本は、卒業後に読んだ 2 冊目の専門書です。仕事中に読んだ最初の本は、具体的な実装をコード レベルでよりエレガントにする方法を教えていました。この本の目的は、抽象化能力、トップレベルの設計、およびドメイン モデリング能力を向上させることです。この本を読む過程で、この本は、チームとプロジェクト モジュール間の境界をどのように定義するかなど、前作での多くの混乱を解決しました。ますます制御不能になっていく結末からプロジェクト コードを抜け出す良い方法はあるでしょうか? さらに、より重要なのは、本を読む過程で、その内容についての考え方を作品自体に限定すべきではなく、そこに含まれるアイデアは、人生の分野での問題をモデル化し、作品の斬新さと美しさを体験する方法を完全にガイドすることができるということです。人生。この本には共鳴する部分が多く、内容も豊富です。実務経験が不足しているため、深く理解できません。現時点では、この記念碑の本質をまだほとんど理解していません。楽しみにしています。この本に書かれていることを今後の仕事や生活の中で確認し、理解して、皆さんを勇気づけていきたいと思います!

パート 1 ドメイン モデルの使用

1. ドメイン駆動設計におけるモデルの役割は何ですか?

  1. モデルとデザインコアの相互作用
  2. モデルは、チームのすべてのメンバーが使用する共通言語のバックボーンです。モデルと実装の間の関連付けのおかげで、開発者はこの言語を使用してプログラムについて話し合うことができます。
  3. モデルには知識が凝縮されています

2. ソフトウェアの中核は何ですか?
ソフトウェアの中心となるのは、ユーザーのドメイン関連の問題を解決する機能です。他のすべての機能は、どれほど重要であっても、
この基本的な目的を果たします。
3. モデルと実装のバインディング

ソフトウェアが概念なしで設計されている場合、ソフトウェアはせいぜい機械化された製品であり、
それが機能する理由を説明することなく有用な機能を実行します。

プログラム設計全体またはそのコア部分がドメイン モデルに対応していない場合、そのモデルには価値がなく、ソフトウェアの正確性が疑われます。同時に、モデルと設計機能の間の複雑すぎる対応関係を理解するのが難しく、
実際のプロジェクトでは、設計が変更されたときにこの関係を維持することが不可能です。分析と設計の間に重大な乖離がある場合、分析活動と設計活動で得られた知識を相互に共有することはできません

ソフトウェア システムの各部分の設計は、ドメイン モデル間の明確な対応を反映するために、ドメイン モデルを忠実に反映する必要があります。より深い領域の概念を反映しようとする場合でも、ソフトウェアがモデルをより自然に実装できるように、モデルを繰り返しチェックして変更する必要があります。私たちが必要とするモデルは、これら 2 つの要件を満たすだけでなく、堅牢な UBIQUITOUS LANGUAGE (世界共通言語) をサポートする必要があります。プログラム設計および基本的な責任の割り当てに関する用語は、モデルから導出されます。プログラム コードをモデルの表現とし、コードの変更はモデルの変更になる可能性があります。そして、その影響は、次の対応するプロジェクト活動にも影響を与えることは間違いありません。モデルに完全に依存する実装には通常、オブジェクト指向プログラミングなどのモデリング パラダイムをサポートするソフトウェア開発ツールと言語が必要です。

4. ユーザーにとってモデルはなぜ重要ですか?

ユーザーとドメイン専門家の基本的な懸念を反映するモデルに基づいてプログラムが設計されると、その設計は、他の方法で行う場合よりもその意図をユーザーに明確に伝えることができます。ユーザーにモデルを理解させることで、
ソフトウェアの可能性を活用する機会が増え、ソフトウェアの動作が合理的で一貫性のあるものになります。

  1. HANDS-ON MODELER(ハンズオンモデラー)

コードを作成する人がモデルに責任があると考えていない場合、またはモデルをアプリケーションに提供する方法を知らない場合、モデルはプログラムとは何の関係もありません。開発者が、コードの変更がモデルの変更を意味することを理解していないと、プログラムのリファクタリングはモデルを強化するだけでなく、弱体化させることになります。同様に、モデラーがプログラム実装のプロセスに参加しない場合、プログラム実装に対する制約は個人的には感じられず、たとえあったとしてもすぐに忘れられてしまいます。モデル駆動設計の 2 つの基本要素のうち 1 つ (つまり、モデルは効果的な実装と抽象的な主要領域の知識をサポートする必要がある) が失われ、最終的なモデルは実用的ではなくなります。最後に、分業によって設計者と開発者の連携が阻害され、MODEL-DRIVEN DESIGNの実現内容を伝えることができなければ、経験豊富な設計者の知識や技術を開発者に伝えることができなくなります。

モデリングに関わる技術者は、プロジェクトの主な責任に関係なく、時間をかけてコードを理解する必要があります。コードの変更を担当する人は、コードでモデルを表現する方法を学ぶ必要があります。すべての開発者は、さまざまな程度でモデルのディスカッションに参加し、ドメインの専門家との連絡を維持する必要があります。さまざまな仕事に携わる人々が、ユビキタスランゲージを通じてコードを触る人たちとモデルについての意見をタイムリーに意識的に交換しなければなりません。

パート II モデル駆動設計の構成要素

画像.png

1. なぜ階層化されたアーキテクチャがあるのですか?

オブジェクト指向プログラムでは、ユーザー インターフェイスやデータベース アクセスなどのサポート コードがビジネス オブジェクトに直接記述されることがよくあります。また、一部のビジネス ロジックはユーザー インターフェイス コンポーネントとデータベース スクリプトに埋め込まれます。これは、開発作業を最短の方法で完了するために行われます。
ドメイン関連のコードが他の多数のコードに散在している場合、ドメイン コードの表示と分析が非常に困難になる可能性があります。ユーザー インターフェイスの単純な変更は実際にビジネス ロジックを変更する可能性が高く、ビジネス ルールの調整にはユーザー インターフェイス コード、データベース操作コード、またはその他のプログラム要素の慎重なスクリーニングが必要になる可能性があります。これにより、一貫したモデル駆動型のオブジェクトを実現する可能性が低くなり、自動テストが困難になります。プログラム内のさまざまなアクティビティに膨大な量のロジックとテクノロジが含まれることを考えると、プログラム自体はシンプルで単純でなければならず、そうでないと理解できないものになってしまいます。

複雑なアプリケーションを階層化します。各レイヤー内を個別に設計することで、レイヤーが一貫性を持ち、その下のレイヤーのみに依存するようにします。標準的なアーキテクチャ パターンを採用し、上位層とのみ疎結合します。ドメイン モデルに関連するすべてのコードを 1 つのレイヤーに配置し、ユーザー インターフェイス、アプリケーション、インフラストラクチャ コードから分離します。ドメイン オブジェクトは、それ自体の表示やストレージの問題やアプリケーション タスクの管理などを考慮せず、ドメイン モデルを表現する方法に重点を置く必要があります。これにより、モデルは重要なビジネス知識を取得して効果的に使用するのに十分な意味があり、十分に構造化されます。

2. SMART UIの「アンチパターン」

経験の浅いプロジェクト チームが単純なプロジェクトを完了したいのに、モデル駆動設計とレイヤード アーキテクチャを使用することに決めた場合、プロジェクト チームは困難な学習プロセスを経験することになります。チームメンバーは複雑な新しいテクノロジーを習得し、オブジェクトモデリングを苦労して学ばなければなりませんでした。(この本の助けを借りても、これは依然として難しいタスクです!) インフラストラクチャとレイヤーの管理により、単純なタスクが完了するまでに長い時間がかかります。単純なプロジェクトは開発サイクルが短く、期待値も低くなります。そのため、プロジェクト チームがタスクを完了するずっと前に、プロジェクトは中止されることになり、ましてやこのアプローチの多くの刺激的な可能性を実証することはできませんでした。
プロジェクトにもっと時間がかかっても、専門家の助けがなければチームメンバーがこれらのテクニックを習得する可能性は低くなります。結局、これらの困難を乗り越えたとしても、おそらくシンプルなシステムを開発するだけでしょう。このプロジェクトには豊富な機能は必要ないからです。

したがって:

すべてのビジネス ロジックをユーザー インターフェイスに実装します。アプリケーションプログラムを小さな機能モジュールに分割し、それぞれをユーザーインターフェースに実装し、その中にビジネスルールを埋め込みます。リレーショナル データベースを共有データ リポジトリとして使用します。利用可能な最も自動化されたユーザー インターフェイス作成ツールとビジュアル プログラミング ツールを使用します。

3. ソフトウェアで表現されるモデルは?

  1. アソシエーション: モデル内のすべての走査可能なアソシエーションは、ソフトウェア内で同じ属性メカニズムを持っている必要があります。
  2. ENTITY : 一部のオブジェクトは、主にその属性によって定義されていません。それらは実際には「アイデンティティの糸」(A Thread of Identity) を表しており、時間を超えて複数の異なる表現を経ることがよくあります。場合によっては、そのようなオブジェクトを、異なるプロパティを持つ別のオブジェクトと一致させる必要があります。また、場合によっては、オブジェクトを同じプロパティを持つ別のオブジェクトと区別する必要があります。識別が間違っていると、データが破損する可能性があります。主にアイデンティティによって定義されるオブジェクトはENTITYと呼ばれます
  3. VALUE OBJECT : 概念的な同一性を持たずにドメインの側面を記述するために使用されるオブジェクトは、VALUE OBJECT (値オブジェクト) と呼ばれます。
    VALUEOBJECT がインスタンス化された後、それはいくつかのデザイン要素を表すために使用されます。これらのデザイン要素については、それが誰であるかではなく、それが何であるかのみを考慮します。
  4. サービス: 場合によっては、オブジェクトは物ではありません。場合によっては、最も明確で最も実用的な設計には、概念的にはどのオブジェクトにも属さない特別な操作が含まれることがあります。それらを強制的に 1 つのカテゴリに分類するのではなく、SERVICE (サービス) という新しい要素をモデルに自然に導入する方が良いでしょう。

ドメイン内の重要なプロセスまたは変換操作が ENTITY または VALUE OBJECT の本来の責任ではない場合、操作を独立したインターフェイスとしてモデルに追加し、SERVICE として宣言する必要があります。インターフェイスを定義するときはモデル言語を使用し、操作名がユビキタス言語の用語であることを確認してください。また、SERVICE はステートレスにする必要があります。

  1. MODULE: : MODULE はモデルを観察する 2 つの方法を提供します。1 つはモデル全体に​​圧倒されずに MODULE の詳細を観察する方法、もう 1 つは内部の詳細を考慮せずにモジュール間の関係を観察する方法です。モジュールは、より大きな観点からドメインを説明します。

誰もがモジュールを使用していますが、モジュールをモデルの本格的な部分として認識している人はほとんどいません。コードは、技術的なアーキテクチャに応じて、または開発者のタスクの分割に応じて、さまざまなカテゴリに分類されます。リファクタリングを頻繁に行う開発者でも、プロジェクトの早い段階で作成された一部のモジュールを使用する傾向があります。
ご存知のとおり、モジュール間の結合は低く、モジュール内部の凝集性は高くなければなりません。結合と結合を解釈すると、MODULE は関連性と相互作用の分布に基づいて機械的に判断されるかのように、テクニカル指標のように聞こえます。ただし、MODULE は単なるコードの分割ではなく、概念の分割でもあります。人が一度に考慮することは限られています (したがって、低結合性が必要です)。支離滅裂な思考は、「ワンポット粥」の思考と同じくらい理解しにくいです (したがって、凝集性が高くなります)。

したがって:

システムを説明できるモジュールを選択し、それに一貫した概念セットを含めるようにします。これにより通常、モジュール間の結合が低くなりますが、これが理想的でない場合は、モデルを変更して概念間の結合を取り除く方法を探すか、モジュールの基礎として使用できる概念 (この概念) を見つける必要があります。以前は見落とされていたかもしれません。)、この概念に基づいて編成されたモジュールは、意味のある方法で要素をグループ化できます。概念を互いに独立して理解および分析できるように、概念を整理する疎結合の方法を見つけます。モデルは、対応するコードを結合することなく、高レベルのドメイン概念に従って分割できるまで改良されます。
モジュール名はユビキタス言語の用語にしてください。モジュールとその名前は、ドメインに関する深い知識を反映している必要があります。

4. ドメインオブジェクトのライフサイクル

画像.png

1. AGGREGATE
抽象化を使用してモデル内の参照をカプセル化する必要があります。AGGREGATE は関連するオブジェクトの集合であり、
データ変更の単位と見なされます。各 AGGREGATE にはルート (ルート) と境界 (境界) があります。境界は、AGGREGATE の内部にあるものを定義します。ルートは、AGGREGATE に含まれる特定の ENTITY です。AGGREGATE の場合、外部オブジェクトはルートのみを参照できますが、境界内のオブジェクトは相互に参照できます。ルート以外の ENTITY にはローカル ID がありますが、外部オブジェクトはルート ENTITY 以外のオブジェクトを認識できないため、これらの ID は AGGREGATE 内で区別する必要があるだけです。

ENTITY と VALUE OBJECT をカテゴリごとに AGGREGATE に集め、各 AGGREGATE の境界を定義する必要があります。各 AGGREGATE で、ルートとして ENTITY を選択し、ルートを介して境界内の他のオブジェクトへのすべてのアクセスを制御します。外部オブジェクトのみがルートへの参照を保持できます。内部メンバーへの一時参照は渡すことができますが、それは 1 つの操作に対してのみです。ルートはアクセスを制御するため、内部オブジェクトを変更するためにルートをバイパスすることはできません。この設計は、AGGREGATE 内のオブジェクトがすべての固定ルールを満たすことを保証し、状態が変化したときに AGGREGATE 全体が固定ルールを満たすことを保証するのに役立ちます。

2. 工場

オブジェクトの作成自体は主要な操作になる可能性がありますが、作成されるオブジェクトは複雑なアセンブリ操作にはあまり適していません。これらの責任を混在させると、設計が十分に理解されなくなる可能性があります。クライアントにオブジェクトの作成を直接担当させると、クライアントの設計が台無しになり、アセンブルされたオブジェクトまたは AGGREGATE のカプセル化が壊れ、クライアントと作成されるオブジェクトの実装との間の結合が密になりすぎます。

複雑なオブジェクトの作成はドメイン層の責任ですが、このタスクはモデルを表すために使用されるオブジェクトには属しません。

したがって:

複雑なオブジェクトと AGGREGATE のインスタンスを作成する責任は別のオブジェクトに移す必要があります。そのオブジェクト自体はドメイン モデル内で責任を持たない可能性がありますが、依然としてドメイン設計の一部です。すべての複雑なアセンブリ操作をカプセル化するインターフェイスを提供します。このインターフェイスでは、クライアントがインスタンス化されるオブジェクトの具象クラスを参照する必要がありません。AGGREGATE 全体を作成し、固定ルールを満たしていることを確認します。

3. リポジトリ

ドメイン駆動設計の目標は、テクノロジーではなくドメイン モデルに焦点を当てて、より優れたソフトウェアを作成することです。開発者が SQL クエリを構築してインフラストラクチャ層の特定のクエリ サービスに渡し、得られたテーブル行データの結果セットに従って必要な情報を抽出し、最後にその情報をコンストラクターまたは FACTORY に渡すとします。開発者がこの一連の操作を実行すると、モデルには焦点が当てられなくなります。私たちは当然のことながら、オブジェクトをクエリされたデータを保存するコンテナーと見なすため、設計全体がデータ処理スタイルに向けられます。正確な技術的な詳細は異なりますが、問題は残ります。クライアントが扱うのはモデルのコンセプトではなくテクノロジーです。

クライアントは、既存のドメイン オブジェクトへの参照を取得する効率的な方法を必要としています。インフラストラクチャがこの機能を提供していれば、開発者は通過可能な関連付けを多数追加できるため、モデルが非常に乱雑になってしまいます。一方、開発者は、クエリを使用してデータベースから必要なデータを抽出したり、特定のオブジェクトを AGGREGATE のルート経由で取得するのではなく直接抽出したりすることもできます。その結果、ドメイン ロジックがクエリとクライアント コードに組み込まれ、ENTITY と VALUE OBJECT は単なるデータ コンテナーになります。データベース アクセスを処理する技術的な複雑さのほとんどを採用すると、クライアント コードがすぐに乱雑になり、開発者がドメイン層を簡素化し、最終的にはモデルが無関係になってしまいます。

ランダムなデータベース クエリにより、ドメイン オブジェクトのカプセル化と AGGREGATE が破壊される可能性があります。技術インフラストラクチャとデータベース アクセス メカニズムが公開されると、クライアントは複雑になり、モデル駆動型の
設計が妨げられます。

本当に直接アクセスが必要な AGGREGATE ルートに対してのみ REPOSITORY を提供してください。顧客は常にモデルに集中し、すべてのオブジェクト ストレージとアクセス操作を REPOSITORY に任せることができます。

5. あまり明白ではない概念をどのようにモデル化しますか?

  • 表示される制約: 制約の詳細を個別に抽象化し、概念を明示的に表現します。
  • プロセスをドメイン オブジェクトとしてモデル化する: 制約とプロセスは 2 つの主要なタイプのモデル概念です。オブジェクトはプロセスをカプセル化するために使用されるため、オブジェクトのビジネス目的または意図のみを考慮する必要があります。典型的なのは、実際に私たちがよく使う戦略パターンです
  • 仕様: ルールをカプセル化します。インターフェースはルールを明示的に表現し、ルールのテストを容易にします。

第三部はリファクタリングで理解を深めます

画像.png

柔軟性の名のもとに、過剰なエンジニアリングが行われる可能性があります。ただし、抽象化と間接的な設計の層が多すぎると、プロジェクトの障害となることがよくあります。実際にユーザーに大きな力をもたらすソフトウェア設計を見てみると、多くの場合、単純なものが見つかるでしょう。シンプルというのは簡単なことではありません。

ドメインの専門家が話す言葉に耳を傾けてください。複雑な概念を簡潔に表現する用語はありますか? あなたの言葉遣いを修正しましたか (おそらく機転を利かせた注意)? あなたが特定の単語表現を使用したときに彼らの顔にあった当惑の表情は消えましたか? これらはすべて、モデルを改善する可能性のある概念を示唆しています。

1. 意図を明らかにするインターフェース

開発者がコンポーネントを使用するためにその実装を検討する必要がある場合、カプセル化の価値は失われます。誰かが開発したオブジェクトまたは操作が他の人によって使用される場合、このコンポーネントを使用する新しい開発者がその実装に基づいてその用途を推測する必要がある場合、彼が推測したことはその操作またはクラスの主な目的ではない可能性があります。それがそのコンポーネントの目的ではない場合、コードは当面は機能しますが、設計の概念的な基礎が誤って使用されており、2 人の開発者の意図が分かれています。

2. 副作用のない機能

複数のルールの計算の相互作用または組み合わせの結果を予測することは困難です。開発者がオペレーションを呼び出すとき、オペレーションの結果を予測するには、その実装と、それが呼び出す他のメソッドの実装を理解する必要があります。開発者が「インターフェイスのベールを剥がす」必要がある場合、インターフェイスの抽象化は制限されます。結果を安全に予測できる抽象化がなければ、開発者は「組み合わせ爆発」1 を制限する必要があり、システムの動作の豊かさが制限されます。

したがって:

関数は明らかな副作用がなく結果のみを返す操作であるため、プログラムのロジックはできる限り関数内に配置してください。コマンド (明らかな状態変化を引き起こすメソッド) を、ドメイン情報を返さない非常に単純な操作に厳密に分離します。複雑なロジックの役割を担うのに非常に適した概念が見つかったら、この複雑なロジックを VALUE OBJECT に移動することで、副作用をさらに制御できます。

3. 主張

操作の副作用がその実装によって暗黙的にのみ定義されている場合、多数の呼び出し間関係を持つシステムでは原因と結果が混乱してしまいます。プログラムを理解する唯一の方法は、分岐パスに沿って実行を追跡することです。カプセル化はその価値を完全に失います。具体的な実行を追跡すると、抽象化も無意味になります。

したがって:

演算の事後条件やクラスとAGGREGATEの固定ルールを明確に表現します。ASSERTION をプログラミング言語で直接記述することができない場合は、自動化された単体テストとして記述します。(プロジェクト開発スタイルに適合する場合) ドキュメントや図に書き込むこともできます。
開発者が予想される ASSERTION について推論しやすくなるように、概念的に一貫したモデルを探してください。これにより、学習プロセスがスピードアップされ、コードの不整合が回避されます。

4. 概念的な輪郭

モデルまたはデザインのすべての要素が全体的に大きな構造に配置される場合、それらの機能は重複します。外部インターフェイスは、クライアントが関心のあるすべての情報を提供できるわけではありません。さまざまな概念が混在すると、その意味がわかりにくくなります。
一方で、クラスやメソッドを分割することも無意味な場合があります。これにより、クライアントが複雑になり、クライアント オブジェクトがさまざまな部分がどのように組み合わされるかを理解する必要が生じます。さらに悪いことに、一部の概念が完全に失われる可能性があります。ウラン原子の半分はウランではありません。さらに、粒度の大きさだけが考慮すべき問題ではなく、その粒度がどのような場面で使用されるのかも考慮する必要があります。

したがって:

ドメイン内の重要な部分についての直感を考慮に入れて、設計要素 (操作、インターフェイス、クラス、および AGGREGATE) をまとまりのある単位に分割します。継続的なリファクタリング プロセス中に変化する規則性を観察して安定性を確保し、これらの変化するパターンを説明できる根本的な概念の輪郭を探します。モデルを、ドメインを有用な知識体系にするドメインの一貫した側面と一致させます。

5. スタンドアロンクラス

モジュール内であっても、依存関係が追加されると、設計を理解することがますます難しくなります。これが
私たちの思考に負担を与え、開発者が対応できる設計の複雑さを制限してしまいました。暗黙的な概念は、
明示的な参照よりも負担がかかります。

低結合はオブジェクト設計の重要な要素です。結合を可能な限り低く保ちます。他のすべての無関係な概念をオブジェクトから抽出します
こうすることでクラスは完全に独立したものとなり、個別に学習して理解することができます。このようなそれぞれの独立したクラスにより、
モジュールを理解する負担が大幅に軽減されます。

最も複雑な計算を STANDALONE CLASS (独立したクラス) に抽出してみてください。これを実現する 1 つの方法は次のとおりです。

多くの依存関係を持つクラスから VALUE OBJECT をモデル化します。

低結合は、概念的な過負荷を軽減する最も基本的な方法です。独立したクラスは究極の低結合です。

6. 営業終了

必要に応じて、戻り値の型が引数の型と同じになるように操作を定義します。実装者の状態が計算で使用される場合、実装者は実際には操作のパラメーターであるため、パラメーターと戻り値は実装者と同じ型を持つ必要があります。このような操作は、その型のインスタンスのコレクションに対するクロージャ操作です。クロージャ操作は、他の概念への依存関係を導入することなく、高レベルのインターフェイスを提供します。

このパターンは、VALUE OBJECT 操作でより一般的に使用されます。

7. 宣言的設計

通常、プログラムまたはプログラムの一部を実行可能な仕様 (仕様) として記述するプログラミング方法を指します。宣言的設計を使用する場合、ソフトウェアは実際にはいくつかの非常に正確なプロパティ記述によって管理されます。それはデザインコンセプトであり、働き方であり、そこから伝わるのは「便利は他人に任せ、面倒は自分に任せる」という哲学です。

パート IV 戦略的設計

画像.png

1. BOUNDEDCONTEXT
大規模なプロジェクトには複数のモデルが存在します。また、異なるモデルに基づくコードを組み合わせると、ソフトウェアはバグが多く、信頼性が低く、理解しにくくなります。チームメンバー間のコミュニケーションが混乱してしまいます。どのコンテキストでモデルを使用すべきではないか混乱することがよくあります。
したがって:

モデルが適用されるコンテキストを明示的に定義します。チームの組織、ソフトウェア システムのさまざまな部分の使用法、および物理的表現 (コード、データベース スキーマなど) の観点からモデルの境界を設定します。境界外の問題によって妨げられたり混乱したりすることなく、これらの境界内でモデルの一貫性を厳密に維持します。
2. 継続的な統合

継続的な統合とは、コンテキスト内のすべての作業を十分な頻度でマージし、それらの一貫性を維持することで、モデルが分割されたときに問題を迅速に発見して修正できるようにすることを指します。ドメイン駆動設計の他の方法と同様に、CONTINUOUS INTEGRATION は、(1) モデル概念の統合、(2) 実装の統合という 2 つのレベルで動作します。

したがって:

すべてのコードとその他の実装成果物を頻繁にマージするプロセスを確立し、自動テストを使用してモデルの分割を迅速に特定します。ユビキタス言語の使用を厳守して、さまざまな概念がさまざまな人々の頭の中で進化するときに、全員がそのモデルについて合意に達できるようにします。

3.コンテキストマップ

画像.png

BOUNDED CONTEXT が 1 つだけあると、グローバル ビューが提供されません。他のモデルの状況はまだ不明瞭で、変化している可能性があります。

他のチームの人々は CONTEXT の境界をあまり意識していないため、無意識のうちに境界を曖昧にしたり相互接続を複雑にする変更を加えてしまいます。異なるコンテキストを相互に接続する必要がある場合、それらは互いに重なり合う可能性があります。

したがって:

プロジェクト内で役割を果たす各モデルを特定し、その境界コンテキストを定義します。これには、非オブジェクト指向サブシステムの暗黙的モデルが含まれます。それぞれのBOUNDED CONTEXTに名前を付け、その名前をユビキタス言語に追加します。

モデル間の接点を説明し、コミュニケーションに必要な変換を特定し、共有コンテンツを強調表示します。まずは現状を説明。後で変更を加えます。**

レーガン大統領が核兵器削減交渉の際に有名に言ったように、**「信頼せよ、しかし確認せよ」**。この文は二国間関係の核心に触れており、文脈をつなぐもう一つの比喩です。

4. モード: 共有カーネル

両方のチームが共有することに同意したドメイン モデルのサブセットを選択します。もちろん、このモデルのサブセットに加えて、モデル部分に関連するコードのサブセット、またはデータベース設計のサブセットも含まれます。明示的に共有されたコンテンツのこのセクションには特別なステータスがあり、一方のチームが他方のチームに相談せずに変更すべきではありません。機能システムは頻繁に統合する必要がありますが、統合の頻度はチーム内での継続的な統合の頻度よりも低くする必要があります
これらの統合が行われると、両方のチームがテストを実行します。

5. 顧客/サプライヤー開発チーム

旅行チームは上流チームに依存していますが、上流チームは下流チームへの製品の配送に責任を負いません。人間性であれ、時間的プレッシャーであれ、相手チームに影響を与えるために何を利用するかを考えるには、多くの余分なエネルギーが必要です。したがって、チーム間の関係を形式化すると、全員が働きやすくなります。このようにして、両方のユーザー グループのニーズをバランスよく処理し、下流で必要な機能に応じて作業をスケジュールできるように開発プロセスを編成できます。

したがって:

2 つのチームの間には、明確な顧客/サプライヤー関係が確立されています。計画会議では、下流チームは上流チームの顧客になります。下流チームのニーズに基づいて実行する必要があるタスクについて交渉し、予算を立て、全員が双方のコミットメントと進捗状況を認識できるようにします。
両チームは協力して、期待されるインターフェイスを検証する自動受け入れテストを開発します。これらのテストを上流チームのテスト スイートに追加して、継続的統合の一部として実行します。これらのテストにより、上流チームは下流チームへの副作用を心配することなく変更を加えることができます。

6. 順応者

2 つの開発チームに上流/下流の関係がある場合、上流チームに下流チームのニーズを満たすインセンティブがなければ、下流チームは何もできません。上流の開発者は利他主義から約束をするかもしれませんが、それを守らないかもしれません。下流チームは善意を持ってこれらの約束を信じ、決して実現しない機能に基づいて計画を立てます。下流プロジェクトは、チームが最終的に既存の状況を利用して自分自身を守ることを学ぶまで保留することしかできません。下流チームは、ニーズに合わせたインターフェイスを入手できません。

上流のデザインの品質が悪くなく、スタイルに互換性がある場合は、別のモデルを開発しない方が良いでしょう。この場合、CONFORMIST(フォロワー)モードを使用できます。

したがって:

BOUNDED CONTEXT 間の変換の複雑さは、上流チームのモデルに厳密に従うことで取り除くことができます。これにより、下流の設計者のスタイルが制限され、理想的なアプリケーション モデルが得られない可能性がありますが、CONFORMITY パターンを選択すると、統合が大幅に簡素化されます。さらに、これにより、ユビキタス言語をサプライヤー チームと共有できるようになります。ベンダーは運転席にいるので、コミュニケーションを取りやすいのが一番です。彼らは利他的な観点からあなたと情報を共有します。

7. 腐敗防止層

画像.png

分離層を作成して、独自のドメイン モデルに基づいてクライアントに機能を提供します。この層は、システムをほとんどまたはまったく変更せずに、既存のインターフェイスを通じて別のシステムと通信します。この層は内部的に、2 つのモデル間で必要な双方向変換を実行します。

8. セパレートウェイ

統合には常に費用がかかり、場合によってはメリットが小さいこともあります。

したがって:

他のコンテキストとの接続を持たない BOUNDED CONTEXT を宣言すると、開発者はこの小さな範囲内でシンプルで特殊なソリューションを見つけることができます

9. ホストサービスを開く

サブシステムを他の多数のシステムと統合する必要がある場合、統合ごとに変換レイヤーをカスタマイズすると、チームの分析麻痺 (大規模な分析作業に直面してプロジェクトが行き詰まってしまう速度) を遅らせることができます。維持しなければならないことはますます増え、変更を加える際に心配することはますます増えます

したがって:

サブシステムを他のシステムがアクセスできる一連のサービスとして扱うためのプロトコルを定義します。サブシステムと統合する必要がある人が誰でもそれを使用できるように、プロトコルをオープンします。このプロトコルは、個々のチームの特別なニーズを除き、新しい統合ニーズが発生するたびに強化および拡張されます。この特定のニーズに対する解決策は、共有プロトコルをシンプルかつ一貫したものに保つために、ワンオフのトランスフォーマーを使用してプロトコルを強化することです。

10. 出版言語

少し

おすすめ

転載: blog.csdn.net/lsgqjh/article/details/109381682