【发布时间】:2017-01-24 09:33:58
【问题描述】:
我正在尝试使用 DDD 和 onion/hexagonal/clean 架构(使用 Java 和 Spring)来构建应用程序。我发现找到关于概念本身的指导比实际如何实现它们更容易。特别是 DDD 似乎很难找到具有指导意义的示例,因为每个问题都是独一无二的。我在 SO 上看到了许多有用的示例,但我仍然有疑问。我想知道通过我的例子是否会对我和其他人有所帮助。
我希望你能原谅我在这里问了多个问题。这个例子似乎太大了,我在多个问题中重复它没有意义。
上下文:
我们有一个应该显示足球统计信息的应用程序,它具有以下概念(为简单起见,我没有包含所有属性):
- 团队,有很多玩家。
- 播放器。
- 夹具,有 2 队和 2 半。
- 一半,有 2 个 FormationsPlayed 和许多组合。
- FormationPlayed,有很多 PositionsPlayed。
- PositionPlayed,有 1 个 Player 和一个位置值对象。
- 组合,可以是2种,有很多招式。
- Move 可以有 2 种类型,有 1 个玩家和一个事件值对象。
您可以想象,在这里尝试找出哪些东西是聚合根是很棘手的。
- 团队可以独立存在,AR 也是如此。
- 玩家可以独立存在,AR 也是如此。
- Fixture 在删除时也必须删除它的一半,AR 也是如此。
- 一半必须是 Fixture 中的实体。
- FormationPlayed 必须在删除 half 时删除,所以也许这应该是 Half 中的一个实体。
- 在删除 Formation 时必须删除 PositionPlayed,因此请相信这应该是 FormationPlayed 中的一个实体。
- 某种意义上的组合可以独立存在,但与特定的游戏半场相关。也许这可能是一个由最终一致性绑定的 AR。
- 删除组合时必须删除移动,因此请相信这应该是组合中的实体。
问题:
- 您是否发现上述设计中有任何错误?如果是这样,你会改变什么?
- Fixture - Half - FormationPlayed - PositionPlayed 聚合似乎太大,所以我想知道您是否同意使用最终一致性将其拆分为 Fixture - Half 和 FormationPlayed - PositionPlayed。我找不到一个例子是如何用Java实现的?如果 Fixture 被删除,您是否会触发 FixtureDeleted 事件,导致其对应的 FormationPlayed 实体也被删除?
- 我想构建一个不了解其持久化方式的域模型(根据洋葱架构)。我的理解是,这里的域实体不应该有代理键,因为这与持久性有关。我还认为实体应该只通过 id 引用其他聚合中的实体。那么,例如,PositionPlayed 如何在域模型中引用 Player?
- 最初的目的只是让客户端获取数据并显示它。最终,我希望客户能够自己执行 CRUD,并且当这种情况发生时,我希望所有不变量都由域模型保持在一起。拥有两个域模型,一个简单用于数据检索,一个丰富用于稍后执行的操作,是否会简化事情(你能告诉我或指向我解释如何的示例)吗?可以说是两个 BC。我问的原因是,当最初我们只想在数据库中显示统计信息时,提出一个丰富的域模型似乎相当耗时,但我也不想给自己制造麻烦,如果这样做更好的话鉴于以后设想的用例,现在创建一个富域模型。我想知道,如果我要创建一个仅用于数据检索的更简单模型,DDD 中的哪些概念可以忽略(例如,我是否还需要分解大型聚合?)
我希望这一切都有意义。如果需要,显然很乐意进一步解释。意识到我在这里问了很多,我可能混淆了一些想法。非常感谢您对此提供的任何答案和智慧!
【问题讨论】:
-
“可以独立存在”往往被更复杂的域不变量、事务分析和现实生活中的性能问题所取代。域实体不是静态对象,许多域逻辑与它们如何从一种状态转换到另一种状态的更精细细节有关。实体间同步也是一个影响设计的大问题。我建议阅读/观看 Vaughn Vernon 关于聚合设计的任何内容。
-
谢谢@guillaume31。显然,您很好地理解了这个主题。是的,我看过 Vaughn Vernon 关于这个主题的一些演讲——这些演讲非常精彩——但是因为每个问题都是独一无二的,我仍然对如何实际执行他所说的话感到有些困惑。除了我可以在网上找到的书籍、演讲、存储库和答案之外,我对这个主题的指导很少。我的意思是通过搜索找到的一般性谈话或示例只能解决特定问题。
-
@guillaume31 您是否认为富域模型在这种情况下是正确的,您是否知道任何其他可能对这种特殊情况有帮助的特定链接?
-
直觉:需求提出了一个比富域模型/DDD 战术模式(聚合、实体等)更简单的解决方案。Martin Fowler 有一个Domain Logic Patterns 列表,您或许可以选择一个更好的从。您仍然可以使用 DDD 的 strategic 模式,如 here 所述。
-
@guillaume31 非常有帮助,谢谢
标签: java domain-driven-design onion-architecture eventual-consistency