基于ABP实现DDD

  什么是DDD呢?领域驱动设计[DDD]是一种针对复杂需求的软件开发方法。将软件实现与不断发展的模型联系起来,专注于核心领域逻辑,而不是基础设施细节。DDD适用于复杂领域和大规模应用,而不是简单的CRUD应用。它有助于建立一个灵活、模块化和可维护的代码库。


1.《Implementing Domain Driven Design》电子书: https://url39.ctfile.com/f/2501739-610635606-674948?p=2096(访问密码:2096)
2.《基于ABP Framework实现领域驱动设计》电子书: https://url39.ctfile.com/f/2501739-610635608-94e753?p=2096(访问密码:2096)
3.《Mastering ABP Framework》电子书: https://url39.ctfile.com/f/2501739-610635610-9a8f66?p=2096(访问密码:2096)


一.DDD中的领域层和应用层相关概念

DDD主要关注领域层和应用层。

1.DDD中的领域层

领域层中的基本概念有:
(1)实体[Entity]
实体就像面向对象中的对象,它包含属性和方法,并且有唯一的ID。

(2)值对象[Value Object]
值对象是领域中类型的领域对象。这听起来很抽象,举个例子就明白了。比如,订单Order这个聚合根由一系列的属性构成:唯一标识ID、OrderDate、OrderItems、Address等。其中Address就是一个值对象。值对象=值+对象=将一个值用对象的方式进行表述,来表达一个具体的固定不变的概念。

(3)聚合[Aggregate]和聚合根[Aggregate Root]
fd17ee6d0921e3a0051e9b868166663d.png⼀个聚合是一系列对象[实体和值对象]的集合,通过聚合根将所有关联对象绑定在⼀起。比如,Issue聚合是由Issue[聚合根]、Comment[实体]和IssuelLabel[值对象]组成的集合。

(4)仓储[Repository]
仓储接口定义在领域层,实现在基础设施层。为什么需要仓储呢?主要就是解耦数据库,把增删查改等数据库操作和不同类型的数据库解耦。DDD通用原则之一就是数据库独立性原则,领域层和应用层只依赖于仓储接口,并且仓储接口不适合使用用任何ORM特殊对象。

(5)领域服务[Domain Service]
领域服务封装了核心的业务逻辑,它对同一个实体的一个或多个方法进行组合和封装,或对多个不同实体的操作进行组合或编排,对外暴露成领域服务。

(6)规约[Specification]
规约是⼀个命名的、可重⽤的、可组合的和可测试的类,⽤于根据业务规则过滤领域对象。

(7)领域事件[Domain Event]
通过消息队列的方式,比如RabbitMQ等,实现一个特定的领域事件发生时,会通知其它的服务。

2.DDD中的应用层

应用层中的基本概念有:
(1)应用服务[Application Service]
通常应用服务层的输入和输出都是DTO,并且一个应用服务通常被认为是一个事务。

(2)数据传输对象[DTO]
目的主要是解耦应用服务层和展示层。如果没有DTO,那么应用服务层返回的是完整的对象,包含了展示层并不需要的字段,并且也可能泄露了对象字段信息。

(3)工作单元[Unit Of Work]
简单理解就是要么全部成功,要么全部失败。

二.基于ABP模板创建的解决方案结构

基于ABP模板创建的解决方案结构如下所示:d0e824a676f997ab2bc55a06e3d14816.png1.领域层
(1)IssueTracking.Domain[领域层]:该项⽬包含实体、值对象、领域服务、规约、仓储接⼝等。(2)IssueTracking.Domain.Shared[领域共享层]:通常定义的常量和枚举,都放在该项⽬中。

2.应用层
(1)IssueTracking.Application.Contracts[应用契约层]:包含应用服务接口和数据传输对象。该项⽬被应⽤程序客户端引用,比如Web项目、API客户端项目。(2)IssueTracking.Application[应用层]:实现在Contracts项目中定义的接⼝。

3.展示层
(1)IssueTracking.Web[展示层]:这个是前后端不分离的项目命名方式,那么通常是一个ASP.NET Core MVC/Razor Pages应用。

说明:如果是前后端分离的项目,在解决方案中不会包含该项目,而是通过IssueTracking.HttpApi.Host项目提供HTTP API服务,供客户端调用。

4.远程服务层
(1)IssueTracking.HttpApi[远程服务层]:简单理解就是很薄的控制层,该项目主要用于定义HTTP API,即应用服务层的包装器,将它们公开给远程客户端调用。
(2)IssueTracking.HttpApi.Client[远程服务代理层]:当第三方客户端引用该项目时,就可以直接通过依赖注入使用远程服务应用,通过基于ABP的动态C#客户端API代理系统来实现的。

5.基础层
(1)IssueTracking.EntityFrameworkCore:EF Core核心基础依赖项目,包含数据上下文、数据库映射、EF Core仓储实现等。
(2)IssueTracking.EntityFrameworkCore.DbMigrations:用于管理Code First数据迁移的特殊的工具项目。最新ABP中已经移除了该项目,不用了解了。

6.其它层
(1)IssueTracking.DbMigrator:控制台应用程序,主要是迁移数据库结构并初始化种子数据。

三.解决方案中项目依赖关系

该解决方案中项目之间的依赖关系如下:f225b92d3664db14742f44d16c2b4906.png1.Domain.Shared
所有项目直接或间接依赖此项目,此项目中的所有类型都可以被其它项目所引用

2.Domain
仅依赖Domain.Shared项目。

3.Application.Contracts
依赖Domain.Shared项目,可以在DTO中复用Domain.Shared中的类型。

4.Application
依赖Application.Contracts项目,因为此项目需要实现应用服务的接口及接口使用的DTO。另外也依赖Domain项目,因为在应用服务中使用仓储接口或领域对象。

5.EntityFrameworkCore
依赖Domain项目,因为此项目需要将领域对象[实体或值对象]映射到数据库的表,另外还需要实现Domain项目中的仓储接口。

6.HttpApi
依赖Application.Contracts项目,因为Controllers需要注入应用服务接口。

7.HttpApi.Client
依赖Application.Contracts项目,因为此项目需要使用应用服务接口。

8.Web
依赖HttpApi项目,发布定义的HTTP API。另外也间接依赖Application.Contracts项目,可以在页面/组件中使用应用服务。

看上面解决方案依赖关系图的虚线部分,就会发现Web项目依赖于Application和EntityFrameworkCore项目。这是因为Web是一个可部署的项目,在应用时需要应用服务和仓储的实现。这样框架设计的一个弊端就是在展示层中是可以使用实体和EF Core对象的,但这是严格避免的。

四.DDD应用程序执行流程

ca34dfbdd19268d728ed5bd31b84ee6e.png第1步:无论是浏览器中的Web Application,还是远程客户端,它们发起HTTP请求到服务器。

第2步:MVC UI或者HTTP API接收并处理请求,在这个阶段执行AOP逻辑,比如授权、输入验证、异常处理、审计日志、缓存等。MVC Controller在构造函数中注入应用服务接口,调用方法发送和接收DTO对象。

第3步:应用服务使用领域层的对象[实体、仓储接口、领域服务等]来实现用例,在这个阶段同样执行一些AOP逻辑,比如授权、验证、审计日志和工作单元等。一个应用服务方法是一个工作单元,具有原子性。

参考文献:
[1]abp-vnext-pro:https://github.com/WangJunZzz/abp-vnext-pro
[2]iEricLee的ABP博客:https://www.cnblogs.com/YGYH/
[3]cms-kit:https://github.com/abpframework/abp/tree/dev/modules/cms-kit
[4]基于ABP Framework实现领域驱动设计

人工智能干货推荐5802c98b20eac1a70a9b1c6b5792727d.jpeg专注于人工智能领域的技术分享

游戏元宇宙34164849c12facc4d6b45753cb36bdd2.jpeg专注于游戏领域的技术分享

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

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

相关文章

二、通过工厂方法来配置bean

调用静态工厂方法创建 Bean是将对象创建的过程封装到静态方法中. 当客户端需要对象时, 只需要简单地调用静态方法, 而不同关心创建对象的细节. 要声明通过静态方法创建的 Bean, 需要在 Bean 的 class 属性里指定拥有该工厂的方法的类, 同时在 factory-method 属性里指定工厂方法…

【GlobalMapper精品教程】019:基于DSM提取离散随机点的高程信息

本文讲解在globalmapper中,基于DSM提取离散随机点的高程信息,配套数据为data019.rar。 文章目录 1. 离散点创建2. 提取离散点高程信息3. 高程标注1. 离散点创建 本文在ArcGIS中,根据给定的范围,随机生成离散点,如下图: 拓展阅读: ArcGIS根据范围创建随机点教程:【ArcG…

shell脚本注意点

2019独角兽企业重金招聘Python工程师标准>>> 直接命令行写脚本的时候,可以用 ; 分割,或 也可以直接回车,然后在继续写脚本在使用 方括号[ ] 的时候,里面空格两边都必须要有空格,比如 [ $a -gt 3 ] 在方括号…

C语言编程规范--------2 注释

2.1 注释的原则 注释的目的是解释代码的目的、功能和采用的方法,提供代码以外的信息,帮助读者理解代码,防止没必要的重复注释信息。 示例:如下注释意义不大。 /* if receive_flag is TRUE */ if (receive_flag) 而如下的注释则给出…

备战金九银十:RabbitMQ有5种工作模式(6)

RabbitMQ是实现了高级消息队列协议(AMQP)的开源消息代理软件(亦称面向消息的中间件)。RabbitMQ服务器是用Erlang语言编写的,而集群和故障转移是构建在开放电信平台框架上的。所有主要的编程语言均有与代理接口通讯的客…

【GlobalMapper精品教程】020:Lidar点云数据分类(自动分类、手动分类)案例详解

航测点云通常跟DSM一致,即包含植被、房屋等信息,必须进行点云分类、过滤,才能生成准确的高程点、等高线和DEM等地形数据。本文以案例的形式详细讲解globalmapper23中点云工具及使用方法。 文章目录 1. 点云分类2. 创建地面高程格网3. 地形绘制4. 格网转点云5. 点云抽稀6. 点…

社交网络图中结点的“重要性“计算(Dijkstra + SPFA + Floyd + 模板)

题目链接: 无 题目大意: 求一个点到其他所有点的最短距离和,保证图连通。 解题过程: 刚开始用 Floyd 水过的,后来用换了几种方法,不错的模板题,Floyd 的时候,要用 vector 存边&#…

web布局固定宽度+变化宽度实现思路

前言 页面当中常规布局我想大家都会的&#xff0c;但有些布局是常规布局中实现不了的&#xff0c;比如变宽和固宽结合的&#xff0c;需要实现(300px)&#xff0b;(100%&#xff0d;300px)的两列布局。以下样式代码前提均为盒模型为border-sizing 的前提下。 html部分 <div c…

CSS3 nth 伪类选择器

考察下面的 HTML 代码片段&#xff1a; <div><section>section 1</section><section>section 2</section><ul><li>item 1</li><li><ul><li>sub item 1</li><li>sub item 2</li><li>…

RedisCluster的安装、部署、扩容和 Java客户端调用

Redis下载 官网地址&#xff1a;http://redis.io/ 中文官网地址&#xff1a;http://www.redis.cn/ 下载地址&#xff1a;http://download.redis.io/releases/ 安装 # &#xff08;三台&#xff09;安装 C 语言需要的 GCC 环境 yum install -y gcc-c yum install -y wget # 下…

【CloudCompare教程】001:CloudCompare中文版下载与安装图文教程

CloudCompare是一款功能强大的点云后处理软件,本文讲解CloudCompare中文版下载与安装方法。 文章目录 一、CloudCompare下载地址二、CloudCompare安装教程三、CloudCompare中文设置一、CloudCompare下载地址 官方下载地址:http://www.danielgm.net/cc/release/ 二、CloudComp…

ML.NET相关资源整理

在人工智能领域&#xff0c;无论是机器学习&#xff0c;还是深度学习等&#xff0c;Python编程语言都是绝对的主流&#xff0c;尽管底层都是C实现的&#xff0c;似乎人工智能和C#/F#编程语言没什么关系。在人工智能的工程实现&#xff0c;通常都是将Python训练好的人工智能模型…

带参数的宏替换

带参数的宏替换因各种需求叠加&#xff0c;替换规则很怪异&#xff1a; 1、首先将实参替换形参&#xff0c;并展开宏 2、如果1步展开后&#xff0c;有#或者##&#xff0c;那么停止替换。 3、如果1步展开后&#xff0c;没有#或者##&#xff0c;且参数也是宏&#xff0c;那么继续…

JAVA学习日志(7-1-继承)

为什么80%的码农都做不了架构师&#xff1f;>>> 继承 1.提高代码复用性 2.让类与类之间产生关系&#xff0c;有了这个关系才有了多态的特性 **不要为了获取其他类的功能&#xff0c;简化代码而继承&#xff0c; 必须是类与类之间有所属关系才可以继承&#xff0c;所…

BZOJ 1370: [Baltic2003]Gang团伙 [并查集 拆点 | 种类并查集WA]

题意&#xff1a; 朋友的朋友是朋友&#xff0c;敌人的敌人是朋友&#xff1b;朋友形成团伙&#xff0c;求最多有多少团伙 种类并查集WA了一节课&#xff0c;原因是&#xff0c;只有那两种关系才成立&#xff0c;诸如朋友的敌人是朋友之类的都不成立&#xff01; 所以拆点做吧 …

常见Lidar点云数据处理及可视化软件汇总

常见的点云处理及可视化软件有&#xff1a; CloudCompare、Globalmapper、Pix4d、ArcGIS&#xff08;Pro&#xff09;、Lidar 360、PCL等等。 文章目录1. CloudCompare2. Globalmapper3. Pix4d4. ArcGIS&#xff08;Pro&#xff09;5. Lidar 3606. PCL1. CloudCompare CloudCo…

Spring 自带工具类汇总

断言 断言是一个逻辑判断&#xff0c;用于检查不应该发生的情况 Assert 关键字在 JDK1.4 中引入&#xff0c;可通过 JVM 参数-enableassertions开启 SpringBoot 中提供了 Assert 断言工具类&#xff0c;通常用于数据合法性检查 // 要求参数 object 必须为非空&#xff08;Not…

解决new Thread().Start导致高并发CPU 100%的问题

背景之前接手一个项目的时候&#xff0c;发现到处是new Thread(()>{ //do something }).Start();这么做的目的&#xff0c;无非是为了减少页面等待时间提高用户体验&#xff0c;把一些浪费时间的操作放到新线程中在后台运行。问题但是这样带来的问题是大量的创建线程&#x…

基于 HTML5 Canvas 绘制的电信网络拓扑图

电信网结构&#xff08;telecommunication network structure&#xff09;是指电信网各种网路单元按技术要求和经济原则进行组合配置的组合逻辑和配置形式。组合逻辑描述网路功能的体系结构&#xff0c;配置形式描述网路单元的邻接关系&#xff0c;即以交换中心&#xff08;或节…