我目前正在使用这种架构的解决方案:
ApplicationCore
项目(包含域实体和业务逻辑)Infrastructure
项目(包含特定的基础结构代码,例如Entity Framework)WebAPI
项目(用于Angular Front和其他客户端服务的REST API)让我们想象一下一个网络表单,用于创建例如汽车,指定主要信息和零件,并将其发布到控制器动作,例如:
[HttpPut]
public async Task<IActionResult> Create(CarModel carModel)
其中CarModel是:
public class CarModel
{
public string Manufacturer { get; set; }
public string Model { get; set; }
public IEnumerable<CarPartModel> Parts { get; set; }
}
public class CarPartModel
{
public string Name { get; set; }
public IEnumerable<CarPartAttributeModel> Attributes { get; set; }
}
public class CarPartAttributeModel
{
public string Code { get; set; }
public object Value { get; set; }
}
我的业务层将包含带有ICarService
方法的CreateCar
,该方法将检查所有插入的数据以对其进行验证并应用一些规则。现在,我不知道将复杂模型从控制器传递到我的业务逻辑的正确方法是什么。
我想到两个选择:
CarModel
放入我的BLL中,并简单地将其传递给CreateCar
方法CarModel
复制到该DTO以将模型保留在WebAPI
层之内被认为是可接受的或最佳实践?还有第三种选择吗?
这些类型的问题的答案将引起争议,但我将提供我的一般解决方案,您可以根据需要解决的问题。我认为这是一种常见的方法。
我的WebAPI仅与DTO进行交互,因此Create方法将接受CreateCarDto。我假设您的代码中CarModel是类似DTO的对象,而不是您的域对象。 (旁注,REST通常使用POST进行创建,而不使用PUT进行更新)。然后,我的控制器在我的服务上调用Create方法,并将该DTO作为参数传入。然后,服务Create方法就可以完成它-验证(我使用FluentValidation),然后在通过EF完成数据库工作之前,将DTO映射到域对象。
对于您描述的设置,我认为您不需要三层对象(模型/ DTO /域?)。通常,面向公众的东西将与Model / DTO交互,并且核心服务将域对象与那些DTO相互转换。