本文是一篇技术文,结合《实现领域驱动设计》和以往的系统开发经验,
重点解释了业务分析过程中的领域,子域,命令模型和查询模型几个概念。
适合有一定经验的软件开发者和产品经理阅读。
相关概念理解,如有不妥,欢迎指正交流。
一 转变开发者思维方式
面向领域的驱动设计,简称 DDD ,下文中用 DDD替代
基于纯粹属性的思考是以数据为中心的数据模型,以属性为中心,关注的是数据的存储,层次之间的传递方式。
以行为事件思考是以领域和业务价值为中心。行为事件,关注的是场景,闭环和对于业务解决能力的支持。
往往很多程序员在开完需求分析会之后,具体功能的实现就已经心里有谱了,数据存储,层次划分也已然明了。
如果这时候,能够综合场景,业务上客户的业务闭环来思考,就接近于 DDD 的设计思想了。
01 区分属性和行为
领域建模时,考虑什么样的对象做什么样的事情,通过对象行为的命名来体现业务含义。
02 关注业务价值
在 Scrum 开发模型中,对待定项目 backlog item 的评估就是基于业务价值来判断
关注 领域对象/业务对象 对于领域概念/业务概念的表达力。
关注点对应于软件开发中的 关注点分离
之前的一篇随笔,请移步 从业务功能复用演化为业务模式的复用
二 领域和子域
领域是一个组织需要做的事,包括业务范畴和做事方式。
01 边界
DDD 在设计中会不断的强调边界,领域就是这个边界内要解决的问题域。
而核心思想是在于划分领域边界从而来解耦。
我认为领域模型才是 DDD 在微服务设计的关键,只有构建了边界清晰的领域模型的边界,才有可能设计出高质量的微服务。领域和子域实际业务中,是比较难划分的。
在微服务设计时不能脱离领域模型来谈微服务。
以下表格是两个具体的领域以及需要做的事。
界限上下文可以理解为组件
在一个界限上下文/组件/系统中,每一个术语应该仅表示一种领域概念。
像电商系统的顾客,平时所说的系统用户,都是不清晰的概念。应该更加具体和细化,比如 B 端客户,C 端客户。B 端客户又可以分为合作供应商,消费者客户。诸如此类的划分细化。
三 CQRS(命令查询职责分离)
CORS 是 DDD 架构模式中的概念。
对于 Model 的理解,通过定义不同的业务模型,如下图所示,用不同的 Model 区别具体的动作和实体。
下图是以优惠券页面查询这个功能点为例,帮助读者识别请求模型和信息模型。
业务模型对应到技术上来讲是对象。
- 命令(Command)
在对象层面,如果一个方法修改了,该方法便是一个命令(Command),不应该返回数据。通常是返回成功与否。命令最终是一个写操作
- 查询 (Query)
如果一个方法返回了数据,方法便是一个查询 (Query),这样的方法,在代码中会以返回的数据类型进行声明。查询最终是一个读操作。
下图是一张请求体,看实际中的模型命名例子,这样定义模型的方式,就是向 DDD 设计思路靠拢。
用业务域整体的概念思考业务模型
数据有两种类型:
- 状态:状态指你此刻看到的东西,比如说写在银行存折上的余额。
- 事件:事件是修改每个状态的动作,例如银行存折上的每一条交易记录。
可以思考,状态和事件在程序中如何区别。
四 反腐层
写到这里,想到一句话
计算机系统之间,如果要进行信息传递,没有通过增加一层服务解决不了的问题。
这个服务就是反腐层。负责独立于系统之间,进行信息传递的服务。
DDD 中的说法,一个领域中,如果需要使用其它领域的信息,可以通过 AC 进行防腐和转义。
这样减少原有系统的侵入和修改。适用于系统重构,依赖中间件升级等场景。
总结
在技术团队中 DDD 思想的落地困难重重,设计不一定追求完全一致,更多的是逐步演化靠近。
大到一个系统的拆分,小到业务模型的定义实现。
反复琢磨,是提高业务系统的设计能力的有效方法。
end 2022 年 8 月 与北京
认识我
互联网技术人,公众号|视频号「图南日晟」主理人
擅长中小企业 技术服务,软件解决方案落地
致力于用技术能力为企业解决实际问题