回顾: NLayerAppV3 是一个使用. net 2.1 实现的经典 DDD 的分层架构的项目.
NLayerAppV3 是在 NLayerAppV2 的基础上, 使用. net core2.1 进行重新构建的; 它包含了开发人员和架构师都可以重用的 DDD 层.
GitHub 地址: https://github.com/cesarcastrocuba/nlayerappv3
本篇介绍 Distributed Service Layer(分布式服务层)
1,Distributed Service Layer(分布式服务层)
借用 dax.NET 的话:
当应用程序以服务提供商 (Service Provider) 的方式向其它远程应用程序提供业务功能时, 或者应用程序的客户端本身是被部署在另一个远程位置时, 其业务逻辑就必须通过分布式服务层向外界发布.
分布式服务层 (通常被实现为 web Service) 可以根据可配置的通信通道与数据消息格式, 为应用程序提供远程访问的功能. 需要注意的是, 分布式服务层中不应该包含任何业务逻辑的实现.
DistributedServices.MainBoundedContext 项目, 创建的是. net core2.1 webapi 项目.
RESTful 方式
BankAccounts 通过构造函数注入应用层的 IBankAppService 契约, 调用应用层的业务, 对外提供服务; Startup 类中配置 EntityFramework, 各种依赖注入, swagger UI 的相关配置
.net core2 中如何使用 swagger, 网上有好多介绍, 也可以查看其 GitHub:
为了应对服务的版本变化, 使用 swagger 可以实现 API 服务多版本控制, 可以参考这篇文章 https://www.cnblogs.com/intotf/p/10075331.html
进阶: 有了 API 服务, 那么 API 服务的认证和授权问题, 如何解决呢?, 可以使用 identityserver4; 如果只需要认证, 则结合 jwt, 就可以实现.
2, 总结
NLayerAppV3 的基础设施层, 领域层, 应用层, 分布式服务层到目前就基本介绍完了, 我们来总结下
基础设施层
包含了两个部分: Data 部分的 CrossCutting 部分; Data 部分是仓储的层超类型, UOW 以及仓储的实现.
CrossCutting 部分则提供了通用功能的支撑, 目前包含三部分: 适配器, 国际化和验证. 分两个项目, 一个项目是定义契约, 另一个是实现.
领域层, 是核心部分
包含仓储的契约, 实体的接口和基类, 值对象的基类, UOW 契约, 规约等; 聚合的划分, 领域服务等.
应用层
协调领域模型与其它应用, 包含事务调度, UOW, 事务等.
分布式服务层
调用应用层对外提供服务.
3, 调用关系
我们以银行转账业务为例, 说明各层的调用逻辑关系
服务 http://localhost:55638/API/BankAccounts PUT
输入源账户信息, 目标账户信息, 转账金额, 服务接收到的是对应的 DTO 对象;
然后调用应用层的转账方法, 应用层接收参数, 利用仓储调用查找有无对应的账户实体, 如果有, 则开始转账:
开启事务, 调用领域层的转账服务转账, 仓储调用 UOW, 提交, 事务完成, 关闭事务.
银行转账的应用层服务代码
- public void PerformBankTransfer(BankAccountDTO fromAccount, BankAccountDTO toAccount, decimal amount)
- {
- //Application-Logic Process:
- // 1º Get Accounts objects from Repositories
- // 2º Start Transaction
- // 3º Call PerformTransfer method in Domain Service
- // 4º If no exceptions, commit the unit of work and complete transaction
- if (BankAccountHasIdentity(fromAccount)
- &&
- BankAccountHasIdentity(toAccount))
- {
- var source = _bankAccountRepository.Get(fromAccount.Id);
- var target = _bankAccountRepository.Get(toAccount.Id);
- if (source != null & target != null) // if all accounts exist
- {
- using (TransactionScope scope = new TransactionScope())
- {
- //perform transfer
- _transferService.PerformTransfer(amount, source, target);
- //comit unit of work
- _bankAccountRepository.UnitOfWork.Commit();
- //complete transaction
- scope.Complete();
- }
- }
- else
- _logger.LogError(_resources.GetStringResource(LocalizationKeys.Application.error_CannotPerformTransferInvalidAccounts));
- }
- else
- _logger.LogError(_resources.GetStringResource(LocalizationKeys.Application.error_CannotPerformTransferInvalidAccounts));
- }
- View Code
来源: https://www.cnblogs.com/net-yuan/p/NLayerAppV3-Distributed.html