在Web应用程序中分离BLL,PL和DAL

时间:2011-10-19 09:11:29

标签: data-access-layer business-logic-layer presentation-layer

我已经开始开发一个可以有多个表示层的Web应用程序,目前它可以在网上但很快就可以在桌面和其他平台上使用。所以我四处寻找如何做到最好。我发现使用分层方法更好。

我正在考虑将BLL作为可由不同PL访问的Web服务。 BLL将访问DAL以进行特定于数据的操作。 到目前为止一切顺利,但我正在考虑将ASP.NET MVC用于Web应用程序。现在我有点困惑,因为“控制器”基本上包含业务逻辑,对吧。 这是一个不错的选择吗?如果我按照相同的路径,使用MVC和上面提到的图层,我的控制器不一定包含BLL但只会是,有点傻瓜。

这是正确的方法吗?

1 个答案:

答案 0 :(得分:3)

这些是推荐的图层:

  • 演示文稿(MVC,WPF,Whatever): 仅包含表示逻辑(从不包括业务逻辑)控制器仅处理与应用程序/服务层的通信以协调通信。

  • 分布式服务(远程门面): 因为您将拥有许多客户端,其中一些是Windows应用程序,其他客户端是Web应用程序,建议创建一个远程服务层(WCF服务或Web服务),将业务层公开给消费者(最好发送和接收DTO)。

  • 应用层: 处理与域层通信的层,并协调事务逻辑和技术服务,如果您使用DTO,它将域对象转换为DTO,反之亦然

  • 域名层: 包含实体和值对象,这是根据面向对象的域对象封装数据和逻辑而设计的业务逻辑的核心。如果使用存储库模式,它还可以包含存储库接口。逻辑的域和服务,不适合单个实体。

  • 数据访问: 使用像NHibernate或EF这样的ORM或任何数据访问技术将实体映射到数据库表中。

  • 基础设施/普通: 基础设施代码和交叉技术服务,如记录

我将尝试给出每个图层的一个小例子: 假设的不完整示例表示您要激活采购订单

表示层(MVC):

public class PurchaseOrderController
{
  public ActionResult ActivateOrder(int id)
  {
    var response = _orderManagementService.ActivateOrder(id); // Call distributed service (Web Service)

    if(response.Succeed)
      return new SuccessActionResult();
    else
      return new FailedActionResult(response.Reason);
  }
}

分布式服务层(Web服务):

public class OrderManagementWebService : IOrderManagementService
{
  private readonly IOrderExecutionService _orderService;

  public OrderManagementWebService(IOrderExecutionService orderService)
  {
    _orderService = orderService; // Order Service from application service
  }

  public ActivationResult ActivateOrder(int id)
  {
    var response = _orderService.ActivateOrder(id); // Call the application layer to execute the logic
    if(
  }
}

应用层:

public class OrderExecutionService : IOrderExecutionService
{
  private IOrderRepository _orderRepository;

  public OrderExecutionService(IOrderRepository orderRepository)
  {
    _orderRepository = orderRepository;
  }

  public ActivationResult ActivateOrder(int id)
  {
    var order = _orderRepository.GetById(id); // Get the order from repository

    try
    {
      order.Activate(); // Call business logic inside the order entity
      return new ActivationResult { Success = true } ;
    }
    catch(ActivationException ex)
    {
      LogFactory.GetLog().Exception(ex); // Call log from infrastructure layer
      return new ActivationResult { Success = false, Reason = ex.Message } ;
    }
  }
}

域层:

public class PurchaseOrder : Entity
{
  // Properties and fields (Data)
  public int Id { get; private set; }
  public Customer Customer { get; private set; }

  // Methods (contains business logic)
  public void Activate()
  {
     if(Customer.IsBlacklisted)
       throw new InvalidCustomerException(...);

     if(_lineItems.Count == 0)
       throw new NoItemsException(...);

     this.SetStatus(OrderStatus.Active);

     .....
  }
}

存储库(数据访问层):

public class OrderRepository : IOrderRepository
{
  public PurchaseOrder GetById(int id)
  {
    // data access code to access ORM or any data access framework.
  }
}

Infrastrucute:

public class Logger : ILogger
{
  public void Exception(Exception ex)
  {
   // write exception to whatever
  }
}