DDD架构

news/2024/11/28 7:25:36/

原文

一、DDD层级

DDD架构层级为四层:用户接口层,应用层,领域层,基础层

1. 用户接口层

Interfaces 的代码目录结构有:assembler、dto 和 facade 三类

  • Assembler: 实现 DTO 与领域对象之间的相互转换和数据交换。一般来说 Assembler 与 DTO 总是一同出现。

  • Dto: 它是数据传输的载体,内部不存在任何业务逻辑,我们可以通过 DTO 把内部的领域对象与外界隔离。

  • Facade: 提供较粗粒度的调用接口,将用户请求委派给一个或多个应用服务进行处理。

2. 应用层

Application 的代码目录结构有:event 和 service

  • Event(事件):这层目录主要存放事件相关的代码。
    它包括两个子目录:publish 和 subscribe。前者主要存放事件发布相关代码,后者主要存放事件订阅相关代码(事件处理相关的核心业务逻辑在领域层实现)。
    这里提示一下:虽然应用层和领域层都可以进行事件的发布和处理,但为了实现事件的统一管理,我建议你将微服务内所有事件的发布和订阅的处理都统一放到应用层,事件相关的核心业务逻辑实现放在领域层。通过应用层调用领域层服务,来实现完整的事件发布和订阅处理流程。

  • Service(应用服务):这层的服务是应用服务。
    加粗样式应用服务会对多个领域服务或外部应用服务进行封装、编排和组合,对外提供粗粒度的服务。应用服务主要实现服务组合和编排,是一段独立的业务逻辑。你可以将所有应用服务放在一个应用服务类里,也可以把一个应用服务设计为一个应用服务类,以防应用服务类代码量过大

3. 领域层

Domain 是由一个或多个聚合包构成,共同实现领域模型的核心业务逻辑。Aggregate聚合内的代码模型是标准和统一的,包括:entity、event、repository 和 service 四个子目录

  • Aggregate(聚合): 它是聚合软件包的根目录,可以根据实际项目的聚合名称命名,比如权限聚合。
    在聚合内定义聚合根、实体和值对象以及领域服务之间的关系和边界。聚合内实现高内聚的业务逻辑,它的代码可以独立拆分为微服务。
    以聚合为单位的代码放在一个包里的主要目的是为了业务内聚,而更大的目的是为了以后微服务之间聚合的重组。聚合之间清晰的代码边界,可以让你轻松地实现以聚合为单位的微服务重组,在微服务架构演进中有着很重要的作用。

  • Entity(实体): 它存放聚合根、实体、值对象以及工厂模式(Factory)相关代码。
    实体类采用 充血模型,同一实体相关的业务逻辑都在实体类代码中实现。跨实体的业务逻辑代码在领域服务中实现。

  • Event(事件): 它存放事件实体以及与事件活动相关的业务逻辑代码。

  • Service(领域服务): 它存放领域服务代码。
    一个领域服务是多个实体组合出来的一段业务逻辑。你可以将聚合内所有领域服务都放在一个领域服务类中,你也可以把每一个领域服务设计为一个类。如果领域服务内的业务逻辑相对复杂,我建议你将一个领域服务设计为一个领域服务类,避免由于所有领域服务代码都放在一个领域服务类中,而出现代码臃肿的问题。领域服务封装多个实体或方法后向上层提供应用服务调用。

  • Repository(仓储): 它存放所在聚合的查询或持久化领域对象的代码,通常包括仓储接口和仓储实现方法。为了方便聚合的拆分和组合,我们设定了一个原则:一个聚合对应一个仓储

4. 基础层

Infrastructure 的代码目录结构有:config 和 util 两个子目录

  • Config: 主要存放配置相关代码。
  • Util: 主要存放平台、开发框架、消息、数据库、缓存、文件、总线、网关、第三方类库、通用算法等基础代码,你可以为不同的资源类别建立不同的子目录

二、应用

比如创建一个用户的命令:

  1. 用户接口层
    Assembler :将 CustomerDTO 转换为 CustomerEntity
    Dto:接收请求传入的数据 CustomerDTO
    Facade:调用应用层创建用户方法
  2. 应用层
    Event:发布用户创建事件给其它微服务
    Service:内部服务 -> 创建用户,外部服务 -> 创建日志
  3. 领域层
    Aggregate:进入用户聚合目录下(如:CustomerAggregate)
    Entity:用户聚合跟
    Event:创建用户事件
    Service:具体的创建用户逻辑,比如用户是否重复校验,分配初始密码等
    Repository:将用户信息保存到数据库

三、实战

基于 DDD 的微服务设计实例代码详解

个人理解

领域层:聚合根:
Entity 实体层使用充血模型:在属性字段的基础上,增加这个实体类自身的业务
例:假如这个类是用来做订单的,肯定包含金额相关的字段,那么可以直接在属性下面编写计算金额的操作
Repository仓储层,专门存放对数据库的基本的crud的操作,与实际的业务分离

DDD将第三方组件区分的更细,mq,redis这类组件如果后续迭代需要替换中间件,rabbitmq替换为rocketmq,能够更清晰的进行替换


http://www.ppmy.cn/news/979233.html

相关文章

【docker 安装】 与【docker-compose 安装】

不同的操作系统需要不同的docker安装文件:具体下载位置: Docker: https://download.docker.com/linux/static/stable/ docekr-compose:https://github.com/docker/compose/releases 1. 验证客户机器是否有docker 和docker-compose docker -…

Vue源码学习 - 数据响应式原理

目录 前言一、入口查找二、初始化initState()initProps()initData()observe() - Observer的守护ObserverdefineReactive() 三、依赖收集Watcher 和 Dep 通过 例子 对概念有个了解1)什么是Watcher呢?2)Watcher的种类有哪些呢?3&…

【linux】uboot之链接重定向

文章目录 一、uboot中的链接脚本重定向二、具体代码编译器选项uboot中的符号重定向 一、uboot中的链接脚本重定向 在 U-Boot 中,链接脚本(Linker Script)用于指定可执行文件的内存布局和符号表等信息。通过修改链接脚本,可以对程…

于大模型迁移中学习 Docker

最近在做大模型的昇腾迁移,国产化框架踩坑不少,基本一天的工作量相当于之前做纯视觉算法时一周踩过的坑数了。 现在在modelarts上用八卡昇腾910跑llama,不同于之前自己配环境,昇腾生态创新中心都是用的镜像,虽说打包起…

Shell编程基础(三)环境变量 位置变量 系统内置变量

环境变量 & 环境变量环境变量范围父子进程之间有效指定用户有效所有用户有效 位置变量系统内置变量 环境变量 在脚本种直接定义的变量,只能在当前shell进程中使用 若想要在其他shell进程中使用,可以将变量声明为 环境变量 export 变量名 &#xff…

问题解决Can‘t update table ‘category‘ in store

问题描述: 使用spring boot的时,候访问更新数据库内容接口报错: Error updating database. Cause: java.sql.SQLException: Cant update table category in stored function/trigger because it is already used by statement which invoked this stored function/trigger. 问题…

夯实数字化转型安全地基,华东某农商行开源安全治理经验

华东某农村商业银行是一家全国首批组建的股份制农村金融机构。近年来,该农商行坚持“科技强行”战略,进一步夯实数字化核心基础,积极推动金融科技与产品、服务的深度融合,努力拓展数字金融的包容性,让数字金融更有温度…

Java maven project XPathFctory

java Maven project, 更新了一个java库,项目无法编译了, 一直报错:No XPathFctory implementation found for the object model: Java 中 XPathFactory 只有抽象定义,没有具体实现,需要添加实现类,经过百度…