从0开发3D引擎(补充):介绍领域驱动设计
我们使用领域驱动设计(英文缩写为DDD)的方法来设计引擎,在引擎开发的过程中,领域模型会不断地演化。
本文介绍本系列使用的领域驱动设计思想的相关概念和知识点,给出了相关的资料。
上一篇博文
下一篇博文
概览
下面的资料粗略地介绍了DDD的相关知识点:
领域驱动设计学习输出
领域驱动设计(DDD)部分核心概念的个人理解
系统学习资料
相关资料为:
DDD理论学习系列
为什么用DDD
参考领域驱动设计学习输出:
- DDD 帮助解决微服务拆分困境
- DDD 帮助应对系统复杂性
- DDD 帮助统一语言
相关概念
领域模型
领域模型包括领域服务、实体、值对象
相关资料为:
领域驱动设计之实体、值对象、领域服务
DDD 领域驱动设计学习(五)- 实体/值对象/领域服务
领域模型的分类
可分为四类:
- 失血模型
- 贫血模型
- 充血模型
- 胀血模型
相关资料为:
关于领域模型(贫血模型,充血模型)
架构
DDD主要有分层、六边形、洋葱这几种架构。其中,六边形和洋葱架构都运用了依赖倒置,比较类似。
架构资料:
DDD 领域驱动设计学习(四)- 架构(分层/六边形/RESTful)
分层架构资料:
DDD分层架构的三种模式
洋葱架构资料:
The Onion Architecture
数据
相关概念参考领域驱动设计系列(2)浅析VO、DTO、DO、PO的概念、区别和用处:
VO(View Object):视图对象,用于展示层,它的作用是把某个指定页面(或组件)的所有数据封装起来。
DTO(Data Transfer Object):数据传输对象,这个概念来源于J2EE的设计模式,原来的目的是为了EJB的分布式应用提供粗粒度的数据实体,以减少分布式调用的次数,从而提高分布式调用的性能和降低网络负载,但在这里,我泛指用于展示层与服务层之间的数据传输对象。
DO(Domain Object):领域对象,就是从现实世界中抽象出来的有形或无形的业务实体。
PO(Persistent Object):持久化对象,它跟持久层(通常是关系型数据库)的数据结构形成一一对应的映射关系,如果持久层是关系型数据库,那么,数据表中的每个字段(或若干个)就对应PO的一个(或若干个)属性。
相关资料为:
领域驱动设计系列(2)浅析VO、DTO、DO、PO的概念、区别和用处
通用语言,又叫统一语言
相关资料为:
DDD 领域驱动设计学习(一)- 领域模型和统一语言
重读领域驱动设计——如何说好一门通用语言
事件风暴
我们使用事件风暴作为DDD的开始,得到通用语言。
相关资料为:
领域驱动设计: 服务边界划分
使用事件风暴探索业务全景
领域和子域
相关资料为:
DDD理论学习系列(2)-- 领域
限界上下文
相关资料为:
DDD理论学习系列(3)-- 限界上下文
上下文映射图
参考DDD—上下文映射图,上下文之间有下面的关系:
- 合作关系(PS):如果两个限界上下文的团队要么一起成功,要么一起失败,此时他们需要建立起一种合作关系。他们需要协调开发计划和集成管理。
- 共享内核(SK):对模型和代码的共享将产生一种紧密的依赖性,对于设计来说,这种依赖性可好可坏。我们需要为共享的部分模型指定一个显式的边界,并保持共享内核的小型化。共享内核具有特殊的状态,在没有与另一个团队协商的情况下,这种状态是不能改变的。我们应该引入一种持续集成过程来保证共享内核与通用语言的一致性。
- 客户方——供应方开发(CSD):当两个团队处于一种上游-下游关系时,上游团队可能独立于下游团队完成开发,此时下游团队开发可能会受到影响。因此,在上游团队的计划中,我们应该顾及到下游团队的需求。
- 遵奉者(C):在存在上游-下游关系时,如果上游团队已经没有动力提供下游团队之所需,下游团队便孤军无助了。只能盲目地使用上游团队的模型。
- 防腐层(ACL):在集成两个良好的限界上下文时,翻译层可能很简单,甚至可以很优雅地实现。但是,当共享内核、合作关系或客户方-供应方关系无法顺利实现时,此时的翻译将变得复杂。对于下游客户来说,你需要根据自己的领域模型创建一个单独的层,该层作为上游系统的委派向你的系统提供功能。防腐层通过已有的接口与其他系统交互,而其他系统只需要做很小的修改,甚至无须修改。在防腐层内部,它在你自己的模型和他方模型之间进行翻译转化。
- 开放主机服务(OHS):定义一种协议,让你的子系统通过该协议来访问你的服务。你需要将该协议公开,这样任何与你集成的人都可以使用该协议。在有新的集成需求时,你应该对协议进行改进或者扩展。对于一些特殊的需求,你可以采用一次性的翻译予以处理,这样可以保持协议的简单性和连贯性。
- 发布语言(PL):在两个限界上下文之间翻译模型需要一种公用的语言。此时你应该使用一种发布出来的共享语言来完成集成交流。发布语言通常与开放主机一起使用。
- 另谋他路(S):在确定需求时,我们应该做到坚持到底。如果两套功能没有显著的关系,那么它们也可以被完全解耦的。声明两个限界上下文之间不存在任何关系,这样使得开发者去寻找简单的、专门的方法来解决问题。
相关资料为:
看看上下文映射的清晰视图
DDD—上下文映射图
聚合
聚合Aggregate就是一组相关对象的集合,我们把它作为数据修改和访问的单元。一个聚合包含聚合根、实体和值对象。
相关资料为:
领域模型:聚合、聚合根
领域驱动设计-聚合
在UML中,需要区分聚合关系和组合关系,详见:
浅谈UML中的聚合与组合
服务
服务包括应用服务、领域服务、基础服务。
基础服务是指基础设施中提供的服务,通常用于操作外部,如发送email等。
应用服务和领域服务的相关资料为:
如何分辨应用服务与领域服务
领域驱动设计DDD之领域服务
仓库
我们使用仓库来操作PO。
相关资料为:
DDD理论学习系列(12)-- 仓储