领域模型设计

Posted 宝哥大数据

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了领域模型设计相关的知识,希望对你有一定的参考价值。

一、前言

现代微服务系统一般涉及的业务流程多,系统交互场景丰富,为了合理切分业务领域,恰当定义业务边界,并以此开发出“高内聚,低耦合”的代码,采用DDD(Domain-Driven Design)领域驱动设计思想就能很好地实现这个目标,根据业务领域合理分层软件架构,让系统拓展性更强,结构更清晰,更灵活,复用程度更高,轻松应对各种复杂的业务需求。

二、领域与对象

2.1、什么是对象

对象在面向对象定义之中,也规定了一些基本的特征:

  • (1)封装:保护内部的操作不被破坏;
  • (2)继承:在原本的基础之上继续进行扩充;
  • (3)多态:在一个指定的范围之内进行概念的转换。

2.2、什么是领域驱动设计

领域驱动设计(Domain-Driven Design 简称DDD),是一套综合软件系统分析和设计的面对对象建模方法,采用领域模型概念,统一分析和设计编程,使软件能够更加灵活快速地跟随需求变化。
领域驱动设计的核心在领域模型,领域模型的核心在业务知识。

2.3、什么是领域对象

领域对象(Domain Object)分为实体对象(也称聚合根)和值对象。
实体对象是具有生命周期、有唯一标识、可以通过唯一标识判断相等性、有增改删查操作、可记录状态的对象。
值对象是指起描述作用,无唯一标识、只能通过属性判断是否相等、即时创建、用完就回收的不可变对象。值对象必须通过实体对象进行操作。

2.4、领域模型中的实体类关系

领域模型中的实体类分为四种模型:VO、DTO、DO、PO

  • VO (View Object) 视图对象: 用于展示层,它的作用是把某个指定页面(或组件)的所有数据封装起来。
  • DTO (Data Transfer Object) 数据传输对象:主要用于展示层与服务层之间的数据传输对象
  • DO (Domain Object) 领域对象:就是从现实世界中抽象出来的有形或无形的业务实体。
  • PO (Persistent Object) 持久化对象: 它跟持久层(通常是关系型数据库)的数据结构形成一一对应的映射关系,如果持久层是关系型数据库,那么,数据表中的每个字段就对应PO的一个属性。

各种实体用于不同业务层次之间的交互,并在各层次间实现转化,如下图所示:

2.5、对象和领域的关系

领域是更大的对象,是可以直接产生业务价值的模型,只包含多对象的行为整合,不包含对象的属性,从而实现领域的行为共享。

领域模型是对业务需求的一种抽象,表达了领域概念、领域规则以及领域概念之间的关系。一个好的领域模型是对统一语言的可视化表示,通过它可以减少需求沟通可能出现的歧义;通过提炼领域知识,并运用抽象的领域模型去表达,就可以达到对领域逻辑的化繁为简。模型是封装,实现了对业务细节的隐藏;模型是抽象,提取了领域知识的共同特征,保留了面对变化时能够良好拓展的可能性。

领域模型以可视化的方式清晰地表达了业务含义,我们可以根据这个模型来指导后面的程序设计与编码实现。当增加新的需求或者需求发生变化时,我们能够敏锐地捕捉到现有模型的不匹配之处,并对其进行更新。领域模型传递了知识,可以作为交流的载体,符合人们的心智模型,有利于让开发人员从纷繁复杂的业务中解脱出来。

三、复杂领域设计原则

3.1、拆分子域建立领域模型

根据业务特点考虑流程节点或功能模块边界因素,按领域逐级分解成大小合适的子域,针对子域进行事件风暴,记录领域对象,初步确定各级子域的领域模型。

3.2、领域模型微调

梳理领域内所有子域的领域模型,对各子域模型进行微调,这个过程重点考虑不同聚合对象的重新组合,同步需要考虑子域里对象的聚合边界、服务以及事件之间的依赖关系,确定最终的领域模型。

3.3、微服务设计和拆解

根据领域模型的边界和微服务的拆分原则,完成微服务的拆分和设计。

四、领域驱动设计和实施

4.1、事件风暴

(1)场景分析
根据不同角色和场景,全面梳理从前端操作到后端业务逻辑之间发生的所有操作、命令、领域事件以及外部依赖信息。
(2)领域建模
领域建模是一个收敛的过程。过程分为三步:第一步根据场景分析中的操作集合定义领域实体;第二步根据领域实体业务关联性定义聚合;第三步根据业务和语义边界等因素,定义领域模型。
(3)微服务设计和拆分
综合考虑职责单一性、性能、版本发布频率、团队沟通效率、技术异构等因素,合理设计和拆分微服务。

4.2、领域对象服务矩阵

将事件风暴产生的领域对象按照各自所在的微服务进行分类,定义每个领域对象在微服务中的层、领域类型和依赖的领域对象,主要是为了确定实体、方法、服务等领域对象在架构中的位置以及对象之间的依赖关系,形成服务矩阵,细化了领域对象之间的关系,补充了事件风暴过程中可能遗漏的细节。

4.3、领域模型服务架构

根据领域模型中领域对象的属性和服务矩阵,设计符合领域模型的技术架构,架构要能清晰地体现微服务实体间的联系,各层级之间的关系,以及服务组合和编排的关系。

4.4、代码模型设计

根据DDD技术架构设计,搭建微服务架构体系,定义各层的微服务工程,各层的领域对象所在的包、类、方法、接口,领域中一个聚合对应一个聚合包。

五、领域划分

领域是自上而下的划分,不仅需要在这些相关联的领域有着极其丰富的经验,脑海中有着清晰且成熟的领域模型图。
而自下而上,也就是本文所讲的,主要思想是从需求出发,划分出实体后,对实体进行归类,最终提炼出领域。

  • 1)对需求进行充分分析,提炼通用语言,从通用语言中抽象出实体
  • 2)按照职责相似度,对实体进行归类,抽象出领域
    • 通过上面的步骤,我们得到了很多实体,然后按照职责的相似度对实体进行归类,相似度高的为一类,每一类给他们起一个名字,这就是领域。

六、逻辑架构设计


逻辑架构图主要分为业务层、领域层、数据持久层,其他微服务模块通过zuul网关区分不同业务标识对应的服务路由到业务层,然后业务层通过组合、编排领域层服务,实现业务流程,领域服务操作领域对象(聚合根)和值对象,实现领域对象的属性修改和一系列领域对象行为,调用基础设施层完成完成一系列基础服务和数据库原子操作,实现数据持久化。

七、DDD软件分层设计

7.1、分层概述

(1)业务层system-xxx-application:组合与编排各领域服务,实现业务流程。
(2)springcloud微服务接口jar包system-xxx-feignclient:暴露微服务领域接口。
(3)领域层system-xxx-domain:单领域服务实现。
(4)领域接口jar包 system-xxx-domain-api:定义领域对象和操作接口。
(5)基础设施层system-xxx-infrastructure:数据存储与处理。
(6)公共服务 system-domain-common-xxx:公共配置、工具类。
(7)system-domain-data-config:Spring容器扫描配置

7.2、分层结构图

总体上分为业务层、领域层、基础设施层,前端通过restful方式请求业务层,业务层通过Spring Cloud的FeignClient接口实现远程调用领域层的微服务,领域层通过自定义Spring容器扫描配置注入不同数据源的组件,从而实现多数据源的操作。

7.3、

层级maven依赖关系

参考:

https://blog.csdn.net/u011527491/article/details/107611524
https://blog.csdn.net/ayunnuo/article/details/114531191

以上是关于领域模型设计的主要内容,如果未能解决你的问题,请参考以下文章

Flux 设计模式 - 关于视图概念的歧义

DDD领域驱动设计实战-深入理解实体

领域驱动设计示例

领域事件

4.服务本身。

领域模型驱动设计(DDD)之模型提炼