【基础篇01】领域驱动设计:微服务设计与 DDD

700 阅读11分钟

前言

本文主要主要是针对DDD框架学习,以及在微服务中应用。 文章中有些图来自网络摘抄,如果侵权请联系。

领域驱动设计**(Domain Driven Design,简称 DDD)**

平常在设计后端框架,拆分服务时,经常为拆分粒度进行争执。常见的问题如下:

  1. 项目初期。项目暂时不大,规划大。过度拆分反而导致了项目复杂,如果不拆分后期扩展又会遇到麻烦。加上研发人员都比较有想法,导致分歧。

  2. 项目运行中,基于当前架构不知道怎么拆分,或者是拆分风险无法评估。可能大部分同学为了安全起见,在原来项目上不断改版,最终导致项目无法迭代。

那是否有合适的理论或设计方法来指导微服务设计呢?就是 DDD。那么今天我就给你详细讲解下:微服务设计为什么要选择领域驱动设计?

软件架构模式的演进

软件架构模式大概有三个阶段, 单机、集中式、分布式微服务架构 三个阶段的演进 。

image

**单机模式: **面向过程编程设计方法,围绕着业务 对 数据库进行设计开发,然后客户端开发。

**集中模式:**面向对象设计方法,从下到上出现了各层抽象。

  • 数据访问层(DAL): 其功能主要是负责数据库的访问,对数据访问进行统一控制。

  • 业务逻辑层:是指一个实体单元为了向另一个实体单元提供服务,应该具备的规则与流程。

  • 业务接入层(表示层):负责界面和交互。

这种结构容易让系统变得臃肿、可扩展性和弹性伸缩性差。

**分布式微服务架构:**随着微服务架构理念提出,集中式架构正向分布式微服务架构演进,更好实现服务之间解耦与复用,同时解决集中模式架构出现扩展性和伸缩能力不足问题。

从研发迭代速度方面看三个框架:

在单机和集中系统建设过程中,A 负责提出需求,B 负责需求分析,C 负责系统设计,D 负责代码实现,**流程很长,经手的人也很多,很容易导致信息丢失 。**最后,就很容易导致需求、设计与代码实现的不一致,往往到了软件上线后,我们才发现很多功能并不是自己想要的,或者做出来的功能跟自己提出的需求偏差太大。 (容易带来信息不对称问题)

在单机和集中式架构这两种模式下,软件无法快速响应需求和业务的迅速变化 ,最终错失发展良机。此时,分布式微服务的出现就有点恰逢其时的意思了。

个人观点:

在团队发展不同阶段应该不同架构开发模式。好的架构模式应该是适应业务发展的,并且充分考虑了时间成本、效率、以及业务目标在内的。不可单拎出来讨论某种设计模式好坏

举例:

  1. 曾经有位CTO对累积用户小于500W的新项目,除了数据必须上报外,其他不要求指定必须某种技术。 为啥会这样决策? 可能有以下好处:
  • 公司基建,入手需要一定成本。新项目目标是快速验证项目能不能成。需要快速开发迭代,不需要受到上线等各种约束。

  • 团队构成。新项目往往是来个某个公司一伙人,原始成员在某个领域都是专家,他们已经形成了自己配合模式。强行改变使用指定框架会造成业务成型慢。

从这个决策来看 集中模式 或许会比 分布式微服务模式优势更大。

  1. 成形公司为了提升研发质量 与 研发效率 会采用分布式微服务架构 搞大量基建。 好处也非常明显:
  • 提升效率:防止了不同业务重复代码研发,常见有基础框架出现。

  • 提升质量:研发人员只需关注当前业务,把点做深,质量自然会高。

同样带来负面:上手成本会变大,如果基建做的差,简直是灾难性的。

因此:不可依照以往经验来评价当前架构是否合适,要去理解除了架构设计之外的其他环境,做出理性判断。

微服务设计和拆分的困境

微服务用来解决集中式架构出现的 比如扩展性、弹性伸缩能力、小规模团队的敏捷开发等等。

那就会面对下面几个问题:

  1. 微服务粒度应该多大呀?

  2. 微服务到底应该如何拆分和设计呢?

  3. 微服务的边界应该在哪里?

拆分越细越好吗?

很久以来都没有一套系统的理论和方法可以指导微服务的拆分,包括微服务架构模式的提出者 Martin Fowler 在提出微服务架构的时候,也没有告诉我们究竟应该如何拆分微服务。

微服务不是拆得越小效果越好。 (过度拆分)

这种情况会导致项目成本高,甚至导致 项目复杂度过高,无法上线和运维。

微服务拆分困境产生的根本原因就是 不知道业务或者微服务的边界到底在什么地方 。换句话说,确定了业务边界和应用边界,这个困境也就迎刃而解了。

为什么 DDD 适合微服务?

DDD** 是一种处理高度复杂领域的设计思想 **,它试图分离技术实现的复杂性,并围绕业务概念构建领域模型来控制业务的复杂性,以解决软件难以理解,难以演进的问题。DDD 不是架构,而是一种架构设计方法论 ,它通过边界划分将复杂业务领域简单化,帮我们设计出清晰的领域和应用边界,可以很容易地实现架构演进。

DDD** 包括战略设计和战术设计两部分。**

  • 战略设计主要从业务视角出发 。建立业务领域模型,划分领域边界,建立通用语言的限界上下文,限界上下文可以作为微服务设计的参考边界。 (从业务功能角度拆分设计)

  • **战术设计则从技术视角出发。**侧重于领域模型的技术实现,完成软件开发和落地,包括:聚合根、实体、值对象、领域服务、应用服务和资源库等代码逻辑的设计和实现。 (从技术角度拆分设计)

我们不妨来看看 DDD 是如何进行战略设计的。

** DDD **战略设计会 建立领域模型 ,**领域模型可以用于指导微服务的设计和拆分 **。事件风暴是建立领域模型的主要方法,它是一个从发散到收敛的过程。它通常采用用例分析、场景分析和用户旅程分析,尽可能全面不遗漏地分解业务领域,并梳理领域对象之间的关系,这是一个发散的过程事件风暴过程会产生很多的实体、命令、事件等领域对象,我们将这些领域对象从不同的维度进行聚类,形成如聚合、限界上下文等边界,建立领域模型,这就是一个收敛的过程。

通俗的讲:战略设计就是先把案例、场景分解,产生 实体、命令、事件等。(发散过程) 然后再对实体、命令、事件 进行聚合。(收敛过程)

image

我们可以用三步来划定领域模型和微服务的边界。

  • 第一步:在事件风暴中梳理业务过程中的用户操作、事件以及外部依赖关系等,根据这些要素梳理出领域实体等领域对象。 (梳理业务逻辑,都有哪些输入)

  • 第二步:根据领域实体之间的业务关联性,将业务紧密相关的实体进行组合形成聚合,同时确定聚合中的聚合根、值对象和实体。在这个图里,聚合之间的边界是第一层边界,它们在同一个微服务实例中运行,这个边界是逻辑边界,所以用虚线表示。** (确定哪些是不可拆分的)**

  • 第三步:根据业务及语义边界等因素,将一个或者多个聚合划定在一个限界上下文内,形成领域模型。在这个图里,限界上下文之间的边界是第二层边界,这一层边界可能就是未来微服务的边界,不同限界上下文内的领域逻辑被隔离在不同的微服务实例中运行,物理上相互隔离,所以是物理边界,边界之间用实线来表示。(更大的单一独立功能)

有了这两层边界,微服务的设计就不是什么难事了。

也就是将第三层作为单独微服务。

个人理解:作者在介绍过程中产生了很多新概念,用通俗的话讲,战略设计就是从业务角度拆分功能为独立模块。 只是作者更深入的形成了方法论,形成了一种思想。

DDD 与微服务的关系

有了上面的讲解,现在我们不妨再次总结下 DDD 与微服务的关系。

DDD 是一种架构设计方法,微服务是一种架构风格,两者从本质上都是为了追求高响应力,而从 业务视角 去分离应用系统建设复杂度的手段。两者都强调从业务出发,其核心要义是强调根据业务发展,合理划分领域边界,持续调整现有架构,优化现有代码,以保持架构和代码的生命力,也就是我们常说的演进式架构

  • DDD 主要关注:从业务领域视角划分领域边界,构建通用语言进行高效沟通,通过业务抽象,建立领域模型,维持业务和代码的逻辑一致性。

  • 微服务主要关注:运行时的进程间通信、容错和故障隔离,实现去中心化数据管理和去中心化服务治理,关注微服务的独立开发、测试、构建和部署。

总结

今天我们主要讨论了微服务设计和拆分的难题。通过 DDD 战略设计可以建立领域模型,划定领域边界,解决微服务设计过程中,边界难以划定的难题。如果你的业务焦点在领域和领域逻辑,那么你就可以选择 DDD 作为微服务的设计方法! (可以使用DDD战略设计作为拆分微服务一个手段

更关键的一点是,DDD 不仅可以用于微服务设计,还可以很好地应用于企业中台的设计。如果你的企业正在做中台转型,DDD 将会是一把利器,它可以帮你建立一个非常好的企业级中台业务模型。有关这点你还会在后面的文章中见到详解。

除此之外,DDD 战术设计对设计和开发人员的要求相对较高,实现起来相对复杂。不同企业的研发管理能力和个人开发水平可能会存在差异。尤其对于传统企业而言,在战术设计落地的过程中,可能会存在一定挑战和困难,我建议你和你的公司如果有这方面的想法,就一定要谨慎评估自己的能力,选择最合适的方法落地 DDD。 (到了战术设计阶段会有点难,量力而行)

写在最后

本文主要来源:[领域驱动设计:微服务设计为什么选择DDD]

作者借助新的概念 DDD(领域驱动设计) 一种处理高复杂领域架构设计方法,用在微服务(软件架构)中来解决微服务拆分边界不清问题。

**DDD****设计模式使用有个很大前提是:对业务有很深的了解,并且充分接触业务案例的,否则根本拆分不出来。 但是如果有了很深业务经验,那即使没有了解DDD思想也会拆出相似模块。只是没有形成 DDD设计模式 这样方法论来。 **

把本文作为之前工作经历的一个知识总结,作为系统化出的理论来学习,还是很不错的。 此外作者 用问题方式作为章节,我很喜欢。