领域驱动架构(DDD)建模

一、背景

常见的软件开发方式是拿到产品需求后,直接考虑数据库中表应该如何设计,这种方式已经将设计与业务需求脱节,而更多的是直接考虑应该如何实现了,这有点本末倒置。而DDD是从领域(问题域)为出发点进行的设计方法。

领域驱动设计的核心是“领域”,从一开始就要让团队走到正确的点上。当我们组建好了团队之后,应该从哪里开始?不是UI原型设计,不是架构设计,不是设计数据库,这些事情重要却非最高优先级。用正确的方法做正确的事情,运用领域驱动设计,就是要先识别问题域,进而为团队提炼达成共识的领域知识。要做到这一点,离不开团队各个角色的沟通与协作。

二、DDD 要解决的两个核心问题:
​1. 业务架构
如何合理的设计?
2. 如何使系统架构域业务架构保持一致并具备可持续的扩展?
领域驱动的设计目标:有效建模,并运⽤用领域模型驱动团队进⾏行行沟通分析、设计及开发。

 

三、领域驱设计的核心思想

1、模型与现实业务的统一
・模型和程序设计的核心相互影响。正是模型与实现之间的紧密联系才使模型变得有⽤, 并确保我们在模型中所进行的分析能够转化为最终程序。
・模型与实现之间的这种紧密结合 在维护和后续开发期间也会很有用,因为我们可以基于对模型的理理解来解释代码。
2、统一(业务和技术)语言
・模型是团队所有成员使用的通⽤语⾔的中枢。由于模型与实现之间的关联,开发人员可 以⽤该语⾔来讨论程序。
・他们可以在无需翻译的情况下与领域专家进行沟通。⽽且由于该语言是基于模型的,因此我们可借助自然语⾔对模型本身进行精化。
3、团队的持续学习,消化知识,系统持续的发展
模型是浓缩的知识。模型是团队一致认同的领域知识的组织⽅式
和重要元素的区分⽅ 式。透过我们如何选择术语、分解概念以及将概念联系起来,模型纪录了我们看待领域的⽅式。
当开发⼈员和领域专家在将信息组织为模型时,这一共同的语⾔ (模型) 能够促使 他们⾼效地协作。

四、DDD设计步骤

4.1 基本概念

(1)实体(Entity):一个由它的标识定义的对象叫做实体。通常实体具备唯一ID,能够被持久化,具有业务逻辑,对应现实世界业务对象。

(2)值对象(Value Object):一个没有概念上标识符描述一个领域方面的对象,这些对象是用来表示临时的事物,或者可以认为值对象是实体的属性,这些属性没有特性标识但同时表达了领域中某类含义的概念。通常值对象不具有唯一ID,由对象的属性描述,可以用来传递参数或对实体进行补充描述。

(3)服务(Service):提供的操作是它提供给使用它的客户端,并突出领域对象的关系。所有的Service只负责协调并委派业务逻辑给领域对象进行处理,其本身并真正实现业务逻辑,绝大部分的业务逻辑都由领域对象承载和实现了。Service可与多种组件进行交互,当一个领域操作被视为一个重要的领域概念,一般就作为领域服务,服务是无状态的。

(4)聚合(Aggregate):用来定义领域对象所有权和边界的领域模式,是用来帮助简化模型对象间的关系。通过定义对象之间清晰的所属关系和边界来实现领域模型的内聚,并避免了错综复杂的难以维护的对象关系网的形成。

(5)聚合根(Aggregate Root):每个聚合都有一个根对象(聚合根实体),从外部访问只能通过这个对象。根实体对象有组成聚合所有对象的引用,但是外部对象只能引用根对象实体。只有聚合根才能使用仓储库直接查询,如果根实体被删除,聚合内部的其它对象也将被删除。

(6)仓储(Repository):是用来管理实体的集合,仓储里面存放的对象一定是聚合,原因是domain是以聚合的概念来划分边界的;聚合作为一个整体概念,要么一起被取出来,要么一起被删除。外部访问不会单独对某个聚合内的子对象进行单独操作。因此,我们只对聚合设计仓储。

(7)工厂(Factory):用来封装创建一个复杂对象,尤其是聚合时所需的知识,是将创建对象的细节隐藏起来。如客户传递给工厂一些简单的参数,然后工厂可以在内部创建一个复杂的领域对象,然后返回给客户。

(8)领域事件(Domain Event):是将领域对象从对repository或service的依赖中解脱出来,避免让领域对象对这些设施产生直接依赖。领域事件的触发点在领域模型(domain model)中。就是当领域对象的业务方法需要依赖到这些对象时就发出一个事件,这个事件会被相应的对象监听到并做出处理。

4.2 描述需求

需求描述要点:

(1)在对业务充分沟通和深入理解的基础上,从业务描述中提取名词,作为关键字;

(2)对关键需求点描述的格式应尽量表述为“用户+需求场景+操作对象”,并在团队之间达成共识;

(3)从提取出来的名词中总结实体,形成问题域;

(4)需求描述格式不限,可以用UML提供的方法和图例进行领域模型设计、确定模型之间的关系,也可以用其他传统方式,目标是团队成员理解一致即可。

用UML方法描述需求举例:

4.3、划分领域

(1)领域(Domain):领域就是问题域,一个领域可以拆分为多个子领域(Sub Domain)。

(2)核心子域(Core Domain):子领域中最核心的叫核心子域,团队的核心资源应该用在核心子域上,因为它是产品成败的关键。

(3)支撑子域(Supporting Subdomain):除了Core Domain外,其他的是支撑子域。

(4)通用子域(Generic Subdomain):有些支撑子域比较特殊,因为它解决的是一类通用问题,这类子域我们叫做通用子域。

  通用子域对应的限界上下文,通常会跨多个子域;多个子领域有时会有相交的部分,称作共享内核,体现到代码上就是同一份代码,在多个领域模型中复用,领域示意图如下:

4.4、限界上下文

限界上下文划分依据:

(1)围绕语言定义边界:利用语义相关性和功能相关性对用例归类;

(2)与业务能力保持一致:避免限界上下文工作边界过大;

(3)围绕团队创建上下文:从技术角度考虑重用和变化的应对、遗留系统的集成。

美团抽奖平台上下文映射如下:

4.5、战术建模

(1)实体(Entity):当一个对象由其标识(而不是属性)区分时,这种对象称为实体;

(2)值对象(Value Object):当一个对象用于对事务进行描述而没有唯一标识时,它被称作值对象;

(3)聚合根(Aggregate Root):聚合是一组相关对象的集合,作为一个整体被外界访问,聚合根是这个聚合的根节点;

(4)领域事件:领域事件是对领域内发生的活动进行的建模。

一个手绘的简易建模,如下:

6、用DDD写需求规格说明书

总结利用领域模型产出需求规格说明书的一般步骤:

(1)需求的理解和描述,抽取提炼关键字;

(2)根据需求划分出初步的领域和限界上下文,以及上下文之间的关系;

(3)进一步分析每个上下文内部,识别出哪些是实体,哪些是值对象;

(4)对实体、值对象进行关联和聚合,划分出聚合范畴和聚合根,进行建模;

(5)将每个业务场景流程化,按照场景流程,使用事件编排,定义好事件上下游关系;

(6)在工程中实践领域模型,并在实践中检验模型的合理性,倒推模型中不足的地方并重构。

参考:

领域驱动架构(DDD)建模中的模型到底是什么? - 知乎

一文教会你领域建模-CSDN博客

DDD-领域驱动设计 - 知乎

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/205830.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

记录 | centos源码编译bazel

tensorflow的源码编译依赖于 bazel 这里进行 bazel 的源码编译 1、安装依赖 sudo yum install -y java-11-openjdk sudo yum install -y java-11-openjdk-devel sudo yum install -y protobuf-compiler zip unzip2、知悉要安装的 bazel 的版本 务必安装受支持的 Bazel 版本…

Linux下c开发

编程环境 Linux 下的 C 语言程序设计与在其他环境中的 C 程序设计一样, 主要涉及到编辑器、编译链接器、调试器及项目管理工具。编译流程 编辑器 Linux 中最常用的编辑器有 Vi。编译连接器 编译是指源代码转化生成可执行代码的过程。在 Linux 中,最常用…

网络安全行业大模型调研总结

随着人工智能技术的发展,安全行业大模型SecLLM(security Large Language Model)应运而生,可应用于代码漏洞挖掘、安全智能问答、多源情报整合、勒索情报挖掘、安全评估、安全事件研判等场景。 参考: 1、安全行业大模…

uniapp 打开文件管理器上传(H5、微信小程序、android app三端)文件

H5跟安卓APP 手机打开的效果图&#xff1a; Vue页面&#xff1a; <template><view class"content"><button click"uploadFiles">点击上传</button></view> </template><script>export default {data() {return…

web:[GXYCTF2019]BabyUpload(文件上传、一句话木马、文件过滤)

题目 页面显示为文件上传 随便上传一个文件看看 上传一个文本文件显示 上传了一个图片显示 上传包含一句话木马的图片 上传了一个包含php一句话木马的文件&#xff0c;显示如上 换一个写法 上传成功 尝试上传.htaccess&#xff0c;上传失败&#xff0c;用抓包修改文件后缀 …

LangChain 23 Agents中的Tools用于增强和扩展智能代理agent的功能

LangChain系列文章 LangChain 实现给动物取名字&#xff0c;LangChain 2模块化prompt template并用streamlit生成网站 实现给动物取名字LangChain 3使用Agent访问Wikipedia和llm-math计算狗的平均年龄LangChain 4用向量数据库Faiss存储&#xff0c;读取YouTube的视频文本搜索I…

Apache Flink(四):Flink 其他实时计算框架对比

🏡 个人主页:IT贫道_大数据OLAP体系技术栈,Apache Doris,Clickhouse 技术-CSDN博客 🚩 私聊博主:加入大数据技术讨论群聊,获取更多大数据资料。 🔔 博主个人B栈地址:豹哥教你大数据的个人空间-豹哥教你大数据个人主页-哔哩哔哩视频 根据前文描述我们知道Flink主要处…

LNMP网站架构分布式搭建部署(编译安装)

目录 一、数据库编译安装 二、nginx编译安装 三、php编译安装 三、通过nfs将三台不同的主机资源共享 四、基础测试 五、完成WordPress站点部署 六、完成bbs论坛站点部署 一、数据库编译安装 1、先下载安装包到/opt目录中&#xff0c;最好选择mysql-boost-5.7.44.tar.gz版…

步进电机驱动芯片TB6600HG部分翻译

有些参数没看懂。一边设计&#xff0c;一边修正。 目录 1.芯片梗概 2.引脚配置 1)引脚含义 2)内部逻辑 3.功能详解 1&#xff09;励磁模式设置 2&#xff09;功能设置 3&#xff09;初始模式 4&#xff09;100% 电流设置(电流值) 5&#xff09;OSC 6&#xff09;衰减…

python 使用 AppiumService 类启动appium server

一、前置说明 在Appium的1.6.0版本中引入了AppiumService类&#xff0c;可以很方便的通过该类来管理Appium服务器的启动和停止。 二、操作步骤 import osfrom appium.webdriver.appium_service import AppiumService as OriginalServerfrom libs import pathclass AppiumSer…

windows判断exe应用程序是否在使用的bat脚本

脚本 REM 查询进程是否存在 tasklist|findstr /i "mysqld.exe">nul &&echo y >2.log ||echo n >2.log REM 读取文本内容赋值给变量 set /P resu<2.log if %resu% y (echo process in use ) else (echo process not in use )我们已mysqld.exe…

C++ day58 每日温度 下一个更大元素

题目1&#xff1a;739 每日温度 题目链接&#xff1a;每日温度 对题目的理解 temperature[i]表示每天的温度&#xff0c;返回数组answer&#xff0c;answer[i]指对于第i天&#xff0c;下一个更高温度最近出现在几天后&#xff0c;如果气温在这之后都不会升高&#xff0c;用0…

720度vr虚拟家居展厅提升客户的参观兴致

VR虚拟展厅线上3D交互展示的优势有以下几点&#xff1a; 打破了场馆的展示限制&#xff0c;可展示危险性制品、珍贵稀有物品、超大型设备等&#xff0c;同时提供了更大的展示空间和更丰富的展示内容。 可提供企业真实环境的实时VR全景参观&#xff0c;提升潜在客户信任度。 提供…

JAVA导出PDF(一)

思路一&#xff1a;直接导出pdf 使用freemarker和itext把html转pdf&#xff0c;存在中文乱码&#xff0c;宋体不识别&#xff0c;需下载simsun.ttc字体&#xff0c;空白占位符不识别等等问题&#xff0c;对前端依赖性较大&#xff0c;不推荐&#xff1b; 适用范围&#xff1a;…

批量操作Excel的四个方法(求和、移动、对比、合并)

Excel文件肯定少不了保存大量数据&#xff0c;那么在使用excel的时候会不会要大批量数据进行操作&#xff1f;今天分享4个快速使用excel操作的小技巧。希望能够帮大家提高excel制作效率。 技巧一&#xff1a;快速求和 当你想要分别得到行列的总和&#xff0c;我们可以选中表格…

看图学源码之 CopyOnWriteArrayList 源码分析

基本简介&#xff1a; 是Java中的一个线程安全的List实现&#xff0c;也是ArrayList 的安全版本&#xff0c;所以就不会有ArrayList 的并发修改异常 的问题产生了 原理 每次在对 List 进行修改时&#xff0c;创建一个新的副本&#xff08;即拷贝&#xff09;&#xff0c;而不…

计算机组成原理—存储系统

文章目录 存储系统分层RAM存储器DRAM刷新地址线复用 ROM存储器疑问 提升主存访问速度双端口RAM多模块存储器单体多字存储器多体并行存储器 主容量扩展cache高速缓存器cache与主存映射&#xff08;读策略&#xff09;替换策略cache写策略 存储方式页式存储器虚拟存储器 计组真的…

【EI会议征稿】第三届密码学、网络安全和通信技术国际会议(CNSCT 2024)

第三届密码学、网络安全和通信技术国际会议&#xff08;CNSCT 2024&#xff09; 2024 3rd International Conference on Cryptography, Network Security and Communication Technology 随着互联网和网络应用的不断发展&#xff0c;网络安全在计算机科学中的地位越来越重要&…

2分钟带你了解什么是Vsync

了解Vsync&#xff0c;首先我们需要认知如下问题 什么是GPUCPU在渲染之前起到什么作用什么是帧&#xff0c;帧率什么是画面撕裂 什么是GPU GPU为图形处理器&#xff0c;又称显示核心、视觉处理器、显示芯片。 是一种专门在个人电脑、工作站、游戏机和一些移动设备(如平板电脑…