你的位置:首页 > ASP.net教程

[ASP.net教程]ASP.NET Boilerplate 文档 1.2 多层结构


  • 介绍
  • ABP结构
  • 多层
  • 其它层(通用)
    • 领域(Core)层
    • 应用层
    • 基础层
    • Web & 表示层
  • 其它
  • 总结


介绍

一个应用的代码库的分层是一个广为接受的技术,用来减少复杂度和提高代码复用性。ABP依照DDD理念来分层,在DDD里有4个基本的层:

  • 表示层:为用户提供一个界面。使用应用层来完成用户交互。
  • 应用层:表示层与领域层的媒介。协调服务业对象执行指定的应用任务。
  • 领域层:包含业务对象和业务规则。是整个应用的核心。
  • 基础层:提供支持更高层的通用技术。一个基础层的典型例子是通过ORM框架实现与数据库的交互的仓储,或是实现发送邮件的邮件供应器。

也可以根据需要添加层,例如:

  • 分布服务层:为远程客户端公开应用特性。像Asp.net web API和WCF等。

这些都是以领域为核心的架构的通用层。实现上可能有些细微的差别。

 

ABP架构

层和结构的概览如下:

Layers

PresentationView Models (Javascript), Views (HTML/CSS), Localization, Navigation, Notifications
WebWeb API Controllers, MVC Controllers, OData, ASP.NET Core
ApplicationApplication Services, DTOs, DTO Mappers, Authorization, Session, Audit Logging
Domain (Core)Entities, Value Objects, Repositories, Domain Services, Unit of Work, Domain Events
InfrastructureORM (EntityFramework, NHibernate), DB Migrations, Background Jobs

Others (common)

下图为一个包含5个项目的简单分层应用:

一个层可以实现成一个或多个程序集。在大型项目里可能为第三方依赖创建多个程序集更合适(像此处的EntityFramework),使每个层都有它自己的Context。

 

领域(Core)层

领域层必须实现所有业务规则。

实体:展示数据和领域业务的操作。通常地它们映射到数据库表。

仓储:类似于对象集合,用来获取和持久化实体到数据源(数据库)。领域层定义了仓储,但不实现它们,由基础层来实现它们。

领域事件:定义领域里特定的事件,并触发和处理它们。领域服务利用实体(及其它领域对象)实现那些不属于某个单独实体的业务规则。

工作单元:是一个管理数据库连接和事务的设计模式,跟踪实体变化并保存变化到数据存储。领域层定义了它,但由基础层实现它。

这一层应该尽可能地独立于第三方类库。

 

应用层

应用层包含用于展示层的应用服务。一个应用服务方法可以接收一个DTO(数据传输对象)作为输入,使用这个输入执行一些领域层的操作,并在需要时返回另一个DTO。它不应该接收或返回实体。一个应用服务方法被认为是一个工作单元。用户输入验证也是在这一层实现。建议使用类似于AutoMapper库等工具来映射实体和DTO。这层还包含当前用户信息的会话(Session)。

 

基础层

当领域层定义仓储、工作单元、和其它服务接口后,基础层实现这些商品。用ORM工具(如NHibernate或EntityFramework)实现仓储。ABP已经这此二种ORM框架提供基类。基础层从其它层抽象出对第三方库的依赖。在这层里也可以使用数据迁移。

除了数据访问,我们可能需要为服务供应商进行抽象,例如,我可能使用服务供应商提供的服务发送短讯,我们可以在领域层或应用层定义一个接口来抽象它,然后我们在这层里实现它。

 

Web & 展示层

Web层用Asp.net、Web API和Asp.net Core实现。两种方式都可在单页面应用(SPA)或多页面应用(MPA)中实现,启动模板也都支持这两种方式。

在一个SPA里所有资源只加载一次(或预先加载核心资源然后在有需要时延迟加载其它资源)给客户端(浏览器),后续的与服务器的交互使用AJAX调用,从服务端获取数据后,Html代码在客户端创建。整个页面不再刷新,视图只是在需要时换出换入。现在有很多Javascript SPA框架,例如Angularjs,Backbonejs和Emberjs。ABP可以使用任何一种,但使用示例和一些帮助机制可能使用Angular更容易。

在一个MPA里,客户端发送一个请求到服务端,服务端代码(通常是Asp.net MVC控制器)从数据库获取数据,并Razor渲染视图创建HTML。创建之后的页面被发送回客户端显示。每个新页面会刷新整个页面。不过客户端也可以通过额外的AJAX请求来优化体验。

SPA和MPA涉及到完全不同的结构。一个管理面板的完美选择是SPA,另外方面,一个博客最好选择MPA,因为它更有利于被搜索引擎发现。即便如此,SPA也可以通过工具使得被搜索引擎发现。当然这些都只是通常做法。

SignalR是一个从服务端推送通知给客户端的完美工具。它能给用户带来丰富、实时的体验。

当下在客户端有许多Javascript类和框架。Jquery是最流行并拥有成千的免费插件。当然还有很多工具/框架使得它与HTML和CSS更好地合作。例如,推特的Bootstrap就是一个非常流行的HTML/CSS框架。

ABP提供基础服务,从你的应用服务自动创建一个Web API层,Javascript可以很容易地使用它们。另外,它提供基础服务来管理应用菜单、本地化和语言切换。同时包含一个简单但统一的Javascript  API来简化系统信息和通知的显示。

ABP在服务端自动处理异常并返回一个对应的响应给客户端。

 

其它

ABP使用Castle Windsor框架支持依赖注入。同时使用Log4Net为客户端记录日志,然而,可以很方便地切换日志类库,只是利用Castle的抽象日志基础,而不需要改变代码。

 

总结

ABP协调一些最好的框架/类库与它自身的类和系统来提供一个更好的基础服务,方便使用多层结构创建一个Web应用。同时提供的模板更容易地为你的应用提供多层解决方案。