领域驱动设计系列笔记|入门概念

DDD这个概念相信大家也不陌生,现在网络上到处都是,已经被吹到无所不能,特别是前些年微服务流行之后。本人在18年开始也断断续续也看了不少DDD相关书籍和教程,整理了一些笔记,之前也有用过DDD的思想去进行领域建模和微服务拆分,接下来将会拆分多个章节DDD常见知识点做一些梳理。

1. 什么是DDD

领域驱动设计 (DDD)是一种软件设计方法,专注于根据领域专家的输入对软件进行建模以匹配合适的领域。该名称来自 Eric Evans 2003 年的一本书,该书通过模式目录描述了该方法。

2.DDD的核心定义

  • 领域:简单来说,它是我们构建应用程序基于一定范围的研究对象,即研究领域。例如 一款现金贷产品。又或者 一道土豆炒牛肉

  • 模型:描述领域特定方面的抽象系统,可用于解决与该领域相关的问题。我的理解,建模就是在虚拟的软件世界建立一个反映真实世界物品或者概念的模型。举个例子:现实中的车,在Java世界就变成一个Car的类,在数据库就变成一张表。

  • 通用语言:在谈论上下文中的任何内容时使用的语言和术语。简单来说就是一份让业务人员看得懂的术语,而不是一些只有技术人员才懂的那些晦涩难懂的概念,避免大家对业务流程的理解上有分歧。举个栗子:就像你跟一个外省的同学聊天,为了互相能理解,尽量都说普通话,而不是互相各自说家乡话,这样大家很可能对于同样一件事物的理解就有分歧,程序员和产品经理描述业务流程也一样。

  • 上下文:一个词或语句出现的环境,决定了它的含义。举个栗子:钱对于财务上下文是钱,对于印钞上下文是人民币,对于防伪上下文是钞票。我们平时跟别人聊天也是要基于一个上下文,不然很可能会像鸡跟鸭讲,互相讲得都不是一个概念的东西,每个东西在不同的上下文定义都有可能不同。

3.应用DDD的前提条件

  • 您目前的项目涉及的业务比较复杂
  • 项目团队对面向对象编程/设计有经验和兴趣
  • 您们有相关领域专家可以请教
  • 在前期模型设计有充足的时间(个人觉得并不适合快速试错产品)
  • 你们需要一个可落地的指导思想帮助你们去划分项目模块或服务

4.DDD的构建模块

4.1.战略模式

  • 领域和子域:如上所述,这里领域是指研究领域。如果研究领域太大,可以将其拆分为子域。领域通常被称为问题空间。子域就是这个领域的某一方面的问题以及跟这问题相关的一切。
    举个栗子: 我们研究领域是一款现金贷产品,这个范围太大了,一款现金贷产品有多个组成部分,我们可以将其拆成 用户域、风控域、额度域、交易域等等,这些就是子域,也就是要研究的问题域。

  • 限界上下文:限界上下文一般是跟子域或者域对应。简单理解为子系统或职责分工。举个栗子: 店里的每个角色都有自己的一套职责。厨师和收银员不太可能不时转换角色。

  • 上下文映射:上下文映射显示域、子域及其有界上下文的对应关系。上下文映射还显示了有界上下文之间的依赖关系。这种依赖关系可以是上游或下游。

4.2.战术模式

  • 实体
    • 需要以ID来跟踪变化的对象
    • 数据可变
    • ID相等性。简单来说就是如果ID相等就认为是同一个实体。

举个栗子:大多数航空公司在每个航班上唯一区分每个座位。在这种情况下,每个席位都是一个实体。但是,我们去参加酒席,每张饭桌的座位是不区分的,坐哪里都一样。在这种情况下,座位实际上是一个值对象。

  • 值对象
    • 包含属性但不需要ID跟踪变化的对象。
    • 数据不可变
    • 可复制可替代
    • 属性相等性。简单来说就是如果属性相等就认为是同一个值对象。

举个栗子:人们在使用人民币时,一般不会区分每张唯一的钞票;他们只关心人民币钞票的面值。在这种情况下,人民币钞票是值对象。但是,印钞公司可能会关注每张独特的钞票;在这种情况下,每个钞票都是一个实体。

  • 聚合
    • 事务一致性边界
    • 聚合之前通过聚合根(一般是聚合的同名实体)进行沟通
    • 尽量缩小组合(最终一致性和领域消息)
    • 聚合是创建、发布领域事件和操作资源库的操作主体

举个栗子:学校里的班级打比赛,是通过调动班长来组织对应的班级,而不是直接通过班里的某位同学,这里的班长就是他们班的聚合根。

  • 领域事件
    • 领域中发生任何领域专业感兴趣的事件
    • 领域事件一般由聚合产生
    • 领域事件不是技术概念

举个栗子:额度已过期、额度已变更等。

  • 存储库:存储库在底层存储机制中保存和检索实体或聚合。存储库是域模型的一部分,因此它们应该独立于数据库供应商。

举个栗子:我们实际项目开发,可能底层用的数据库会随着项目需要而改变,它可以帮助我们屏蔽了底层数据库技术实现,让我们可以不需要关注到底用了什么数据库实现框架,只需要关注实体或聚合的操作,如果引用的数据库发生变化,我们也只需要改存储库的部分逻辑,不需要所有模块都改。

  • 模块,也称为Packages:高内聚的组件应该打包在一起。模块由业务依赖项定义,而不是由技术架构定义。
    示例 账单聚合 和 账单仓库 应该放在同一个模块中,因为它们耦合非常紧密。

  • 工厂:用于创建领域对象的方法应该委托给专门的工厂对象,以便可以轻松地互换替代实现。

5.领域驱动设计流程

6.DDD与面向对象的关系

7.DDD与敏捷的关系

7.DDD与微服务的关系

DDD的领域划分思想,很适合用在微服务的服务划分,因为微服务一直以来都没有一个比较理想的划分方式,大多数人都是凭借自己对微服务的理解去划分,导致很多服务严重脱离实际需要,要么划分过细、要么功能过于单一、要么模型脱离实际业务等等,造成资源大量浪费和人力成本的增加。

一般微服务划分可以基于领域驱动设计以下两个维度:

  • 基于聚合划分
  • 基于限界上下文划分(推荐)

网图

后面章节将会详细介绍DDD每一块内容,敬请期待!

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

元学习

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值