继续浏览精彩内容
慕课网APP
程序员的梦工厂
打开
继续
感谢您的支持,我会继续努力的
赞赏金额会直接到老师账户
将二维码发送给自己后长按识别
微信支付
支付宝支付

DDD精粹速读(二)

JavaEdge
关注TA
已关注
手记 394
粉丝 1.4万
获赞 1475

前言

在上一篇文章中,我介绍了领域驱动设计(DDD)的战略设计,以及如何处理大局。本篇文章将深入探讨领域驱动设计(DDD)的核心——战术设计。

Vaughn Vernon 在他的书《Implementing Domain Driven Design》(实现领域驱动设计)中巧妙地将战略设计比作登山者规划攀登路线,而战术设计则比作他们所使用的工具。

战术设计

战术设计为我们提供了有用的指引和结构,帮助我们在***领域模型***中创建丰富且纯粹的业务逻辑表达。当我们需要为一个复杂或潜在复杂的领域建模时,这些指引尤为有价值。

在DDD之外,实体通常会被建模为具有多个属性,这些属性可以被模型代码的调用者(客户端)更改。这样一来,客户端需要自行执行业务规则(例如,价格不能为负)。其结果是,业务逻辑往往分散在我们的应用程序中,通常位于应用层/服务层或控制器中。

战术设计建议我们的领域模型应该是封装所有与系统服务的上下文/子领域相关的业务逻辑的地方。它位于我们应用程序的“核心”,并且不依赖于外部的架构层。

系统的行为通过领域模型的公共方法暴露出来,这些方法代表了用户希望执行的有意义的任务(例如,SubmitOrder,ReserveItem)。模型的客户端***只能***调用模型的这些方法。领域模型是使用统一语言构建的。

战术设计工具箱中,有一些结构使领域建模变得更加简单且有效。

实体

在战术设计中,***实体***是具有身份的事物。其属性可能会随时间而改变,但实体本身依然是同一个实体。实体由其身份定义,而非其属性的值。

例如你,一个人类(显然)。即使你改了名字,你仍然是同一个人类。如果你有一个拥有相同属性的双胞胎,你们两人也不是同一个人类。实体的内在身份独立于其属性。

值对象

值对象,与实体不同,它完全由其值定义,没有身份。例如棕色这种颜色;它无法改变,否则就会变成另一种颜色。它由其值定义且不可变。

一种特别有用的值对象类型是***命令***,它表示系统必须响应的行动请求。

在实体的属性中,应优先使用值对象而非原始类型,以封装与值对象相关的验证或业务逻辑,例如质量不能为负(在大多数领域中!)。

聚合 / 聚合根

通常,我们需要跨多个实体进行验证以强制执行业务规则。

例如,“新用户的电子邮件地址必须唯一”。

为了执行这一规则,我们必须将提供的地址与现有用户的地址进行比较。我们通过在单个对象中构建***聚合体***,即实体和值对象的集合,以便在模型中实现此类验证。

聚合体中的顶级对象称为***聚合根***。聚合体内的对象的变更必须通过聚合根进行。聚合体可以引用其他聚合体,但只能通过聚合根的ID进行引用,以保持封装性。

领域事件

当我们与领域专家交流时,他们经常提到已经发生的事件及对这些事件的响应。我们使用***领域事件***及相应的处理程序来对此进行建模。

有时还包括集成事件,以区分应该在成功的数据库事务之前或之后处理的事件,尽管这也可以通过其他方式处理。

示例

上述四个结构是我们领域模型的核心构建模块,仅凭这些我们就可以对复杂领域进行清晰的建模。

例如一个订单聚合根的方法:Confirm()。在这个方法中,我们可能会验证订单包含一个或多个订单项,并且订单的状态为“待处理”,然后将订单状态更新为“已确认”,并触发一个OrderConfirmed领域事件。我们可以处理此事件,以在其他聚合根中实现副作用,如交付限界上下文中的出货聚合根。

仓储

在DDD中,***仓储***专门操作聚合根。它负责获取聚合根,在此我们可以调用一个公共方法来更改其内部状态,然后持久化更新后的聚合根。流行的ORM已经内置了出色的支持来处理这种场景。仓储的实现不在领域模型内部,尽管其接口/合同可能存在于领域模型中。

应用层服务

应用层服务将来自外部世界的命令/请求路由到我们的模型中。它们构成了一个薄的编排层,在这里注入基础设施问题(如仓储实现),并调用聚合根的相关公共方法。

需要注意的是,应尽量保持应用层服务的“简洁”,我们希望所有的业务逻辑都在应用的核心中。

领域服务

当我们必须在多个聚合体之间协调功能时,会发生什么?这是否构成“业务逻辑”?

是的!一种解决方案是***领域服务***。它类似于应用层服务,但位于核心领域内部。它包含构成业务逻辑的编排逻辑。通常,这一连串的事件通过领域事件及相应的处理程序表达得更好。

总结

如果你只会做基本的算术,数学是有用的。如果你会做张量计算,它也很有用,但你不会从张量计算开始。

以类似的方式,DDD是一门深奥的学科。有很多书籍从高度学术的到极其实用的都有。著名的《蓝皮书》是关于该主题的原始参考文献;它以相当学术的观点提供了对DDD的详细定义。相对的,《红皮书》讲述了三个开发团队在采纳DDD过程中的故事,使得DDD的概念变得自然且实用。对于听觉型学习者,还有许多启发性的演讲,如同事 Andrew Harmel-Law 的演讲。
关注我,紧跟本系列专栏文章,咱们下篇再续!

作者简介:魔都架构师,多家大厂后端一线研发经验,在分布式系统设计、数据平台架构和AI应用开发等领域都有丰富实践经验。

各大技术社区头部专家博主。具有丰富的引领团队经验,深厚业务架构和解决方案的积累。

负责:

  • 中央/分销预订系统性能优化
  • 活动&券等营销中台建设
  • 交易平台及数据中台等架构和开发设计
  • 车联网核心平台-物联网连接平台、大数据平台架构设计及优化
  • LLM Agent应用开发
  • 区块链应用开发
  • 大数据开发挖掘经验
  • 推荐系统项目

目前主攻市级软件项目设计、构建服务全社会的应用系统。

打开App,阅读手记
0人推荐
发表评论
随时随地看视频慕课网APP