这篇文章行文结构对照微软博客, 结合本人意译和多年实践的回顾思考形成此次读书笔记。

Domian-driven Design

领域-驱动-设计(DDD)提倡基于(用例相关的现实业务)进行建模

1. DDD的视角

  • DDD将现实问题视为领域;
  • DDD将独立的问题描述为有界限的上下文(一个有界上下文对应一个微服务),并强调通用语言讨论这些问题

2. DDD提出的概念

许多技术概念和模式,例如充血模型(对应我们常写贫血模型)、值对象、聚合和聚合根规则。

3. 目前实施DDD的现状

有时DDD技术规则和模式被视为障碍/啰嗦,对于实施DDD方法而言,学习曲线比较陡峭。

不要为了实施而实施,最重要的是使用通用语言编写与业务问题一致的领域代码

此外仅当您要实现具有复杂业务规则的微服务时,才应使用DDD方法,诸如CRUD服务之类的简单职责可以通过更简单的方法进行管理。

DDD模式可以协助划分微服务边界

在已经确定的界限上下文,您可以为领域建模:实体模型、值对象和聚合,DDD与边界有关,微服务也与边界有关。

尽量保持小型微服务

划分界限上下文,要平衡两个目标:

  1. 创建尽可能小的微服务(这一点不应该成为主要动力)
  2. 要避免微服务之间过密的通信

这两个目标可能彼此矛盾,两者通过演进的方式达到平衡:

尽可能分解系统,直到在下次分解时感到服务通信迅速增加。

DDD微服务中的层

  1. DDD定义的多层是为了管控代码的复杂性, 这些层是逻辑组件(类似环环相扣的齿轮)。
  2. 不同的层(例如领域模型层与表示层等)可能具有不同的类型,此时层加类型需要转换。

例如从数据库中加载的实体,有时候需要做一下修正(截取部分信息、增加信息)才能适配客户端UI。

  1. 领域模型层中的领域实体不应传播到它不属于的其他区域(如表示层)
  2. 重要的是有一个由聚合根控制的域模型,以确保与该实体组(聚合)相关的所有不变式和规则都是通过单个入口点或(聚合根)执行。

订单DDD微服务有三层:

  • 应用程序层 Ordering.API
  • 领域层 Ordering.Domain
  • 基础设施层 Ordering.Infrastructure

三层形成的类库有清晰且明确的依赖关系

1. The domain model layer

负责表达业务概念、业务场景和业务规则。这一层会将技术细节传递到基础设施层,这一层控制、反映业务场景,是业务软件的核心。

  • 领域模型层是表达业务的地方,在编程上体现为捕获数据和行为(具有逻辑方法)的领域实体的类库

  • 遵循持久性无感知和基础设施无感知原则

领域模型层必须完全忽略数据持久性细节,这些持久性任务应由基础设施层执行,因此,此层不应直接依赖基础设施,这意味着一个重要规则是领域模型实体类应为POCO。

领域实体不应直接依赖于任何数据访问基础框架(EF、NHibernate),理想情况下,您的域实体不应继承自或实现任何基础设施中定义的任何类型。 大多数现代的ORM框架(例如Entity Framework Core)都支持这种方法,因此您的领域模型不会与基础设施耦合。

  • 领域模型中遵循持久性无感知原则很重要,但也不应忽略持久性问题

理解物理数据模型以及它如何映射到您的实体对象模型仍然非常重要,否则你的设计将会是空中楼阁。而且,大多数时候你将本应该采用关系数据库的设计直接迁移到 NoSQL或面向文档的数据库,领域模型层很可能不适用(基于存储技术和ORM技术,您的实体模型仍然必须遵守一些约束条件)。

2.Application Layer

定义软件要执行的工作,并引导(可表达的领域对象)解决问题。

该层对对业务负责,有时会与其他系统的应用程序层交互。

该层保持薄: 它不包含业务规则或知识,而仅协调任务并将工作委托给下一层的域对象协作;

它没有反映业务情况的状态,但是可以具有反映用户或程序的任务进度的状态。

微服务的应用层在.NET中一般表现为WebAPI,webapi实现交互、远程网络连接、为UI/Client app提供的外部请求中转。

再次强调webapi不应该包含业务规则或领域知识(尤其是用于事务或更新的领域规则),这些应归领域模型类库所有。

应用层只能协调任务,不能保存或定义任何域状态(域模型),它将业务规则的执行委托给领域模型类本身(聚合根和域实体),这将最终更新这些域实体中的数据。

总体来看,应用层是为实现前端用例的地方。

3. The infrastructure layer

基础设施层: 定义如何将最初保存在领域实体中的数据持久化到数据库或者其他存储结构的过程。

一个示例是使用Entity Framework Core代码实现存储库模式类: 该存储库模式类使用DBContext将数据持久存储在关系数据库中。

根据前面提到的持久化无感知基础设施无感知原则,基础设施层不得“污染”领域模型层。

再次强调:必须保持领域层实体对基础设施层框架的无感知状态, 领域模型层类库应该只包含领域代码,而只有POCO实体类可以实现软件的核心,并且与基础设施技术完全脱钩。

总结

  1. 在DDD中,应用层依赖于领域和基础设施层,而基础设施依赖于领域层,但是领域层不依赖于任何层。
  2. 只在领域层编写业务规则和通用的领域知识,而应用层负责针对软件的目标来组合、协调领域层的业务规则。
  3. 领域层的领域实体、值类型、聚合根反映了真实业务的核心,需要用一种通用的语言来定义,这样不管应用层多么复杂,核心领域层自岿然不动。
  4. 领域层不能直接依赖与基础设施层,现代ORM框架一般都提出仓储模型来帮助领域层和技术设施层解耦。

翻译自: https://docs.microsoft.com/en-us/dotnet/architecture/microservices/microservice-ddd-cqrs-patterns/ddd-oriented-microservice

[半翻] 设计面向DDD的微服务的更多相关文章

  1. 基于DDD的微服务设计和开发实战

    你是否还在为微服务应该拆多小而争论不休?到底如何才能设计出收放自如的微服务?怎样才能保证业务领域模型与代码模型的一致性?或许本文能帮你找到答案. 本文是基于 DDD 的微服务设计和开发实战篇,通过借鉴 ...

  2. 驱动领域DDD的微服务设计和开发实战

    你是否还在为微服务应该拆多小而争论不休?到底如何才能设计出收放自如的微服务?怎样才能保证业务领域模型与代码模型的一致性?或许本文能帮你找到答案. 本文是基于 DDD 的微服务设计和开发实战篇,通过借鉴 ...

  3. 【DDD/CQRS/微服务架构案例】在Ubuntu 14.04.4 LTS中运行WeText项目的服务端

    在<WeText项目:一个基于.NET实现的DDD.CQRS与微服务架构的演示案例>文章中,我介绍了自己用Visual Studio 2015(C# 6.0 with .NET Frame ...

  4. 可落地的DDD(4)-如何利用DDD进行微服务的划分(2)

    摘要 在前面一篇介绍了如何通过DDD的思想,来调整单体服务内的工程结构,为微服务的拆分做准备.同时介绍了我们在进行微服务拆分的时候踩过的一些坑. 这篇介绍下我们最终的方案,不一定对,欢迎留言讨论. 微 ...

  5. UBer面向领域的微服务体系架构实践

    介绍 最近,人们对面向服务的系统架构和微服务系统架构的缺点进行了大量的讨论.尽管仅仅在几年前,由于微服务体系架构提供了许多好处,如独立部署的灵活性.明确的所有权.提高系统稳定性以及更好地分离关注点等, ...

  6. 可落地的DDD(3)-如何利用DDD进行微服务的划分

    摘要 前面两篇介绍了DDD的目标管理.DDD的工程结构调整.这篇讨论微服务的划分.微服务是目前后端比较流行的架构体系了,那么如何做好一个微服务的划分?一个微服务的粒度应该是多大呢?这篇主要介绍如何结合 ...

  7. .NET 微服务和Docker容器

    .NET 微服务:适用于容器化 .NET 应用的体系结构 容器和 Docker 简介 什么是 Docker? Docker 术语 Docker 容器.映像和注册表 为 Docker 容器选择 .NET ...

  8. DDD之1微服务设计为什么选择DDD

    背景 名词解释 如果你的团队目前正是构建微服务架构风格的软件系统,问自己两个问题? 软件架构演进 软件架构大致经历了从单机架构,集中式架构,分布式微服架构,程序的层次图如下所示. 单机架构 特点如下: ...

  9. 微服务中台落地 中台误区 当中台遇上DDD,我们该如何设计微服务

    小结: 1. 微服务中台不是 /1堆砌技术组件就是中台 /2拥有服务治理就是中台 /3增加部分业务功能就是中台 /4Cloud Native 就是中台 https://mp.weixin.qq.com ...

随机推荐

  1. WEB缓存系统之varnish基础入门(一)

    前文我们聊了下http协议里的缓存控制机制以及varnish架构组件介绍,回顾请参考https://www.cnblogs.com/qiuhom-1874/p/12620538.html:今天我们来聊 ...

  2. 算法修炼之路——【链表】Leetcode24 两两交换链表中的节点

    题目描述 给定一单链表,两两交换其中相邻的节点,并返回交换后的链表. 你不能只是简单的改变节点内部的值,而是需要实际的进行节点交换. 示例: 输入:head = [1, 2, 3, 4] 输出:hea ...

  3. 读者来信 | 如果你家HBase集群Region太多请点进来看看,这个问题你可能会遇到

    前言:<读者来信>是HBase老店开设的一个问答专栏,旨在能为更多的小伙伴解决工作中常遇到的HBase相关的问题.老店会尽力帮大家解决这些问题或帮你发出求救贴,老店希望这会是一个互帮互助的 ...

  4. ARDUINO UNO数字引脚端口上电后不稳定状态。

    ARDUINO UNO数字引脚端口上电后不稳定状态. 在使用4*4矩阵键盘时,遇到了输入端的电平无法稳定,一直被识别为高电平. 在发现这一问题后,首先检查程序是否出错.检查后发现程序没有任何问题. 于 ...

  5. [HOJ2662]Pieces Assignment<状态压缩dp>

    描述: 有一个n*m的棋盘(n.m≤80,n*m≤80)要在棋盘上放k(k≤20)个棋子,使得任意两个棋子不相邻(每个棋子最多和周围4个棋子相邻).求合法的方案总数. 输入: 本题有多组测试数据,每组 ...

  6. phpwind 安装下一步空白解决方案

    系统版本  centos 翻阅网上大部分都是php版本问题,让降级就行了,试了之后根本不行 其实再安装一个插件即可成功 如下: yum install -y php-mysql

  7. Celery动态添加定时任务

    背景 业务需求:用户可创建多个多人任务,需要在任务截止时间前一天提醒所有参与者 技术选型: Celery:分布式任务队列.实现异步与定时 django-celery-beat:实现动态添加定时任务,即 ...

  8. JMeter中聚合报告的各项参数详解

    下面我们来共同学习这些参数的作用: 1.Lable:Label:每个 JMeter 的 element(例如 HTTP Request)都有一个 Name 属性,这里显示的就是 Name 属性的值: ...

  9. JavaScript 进阶入门

    17:56:11 2019-08-09 如题所见 还是入门 23:10:17 2019-08-11 继续学习 16:34:59 2019-08-14 虽然入了门 但还是缺少实践 本文资料来源: 慕课网 ...

  10. 微信号网页版api

    Django Wechat Api djangowechatapi是基于wxpy和django制作的web应用 安装 使用pip pip install djangowechatapi 源码安装 gi ...