asp.net-mvc - 如何使用 Autofac 将 Controller 的 ModelState 传递给我的服务构造函数?

标签 asp.net-mvc autofac

我在 ModelStateDictionary 上有一个包装器,我的所有服务都接受它。是否可以配置autofac将 Controller ModelStateDictionary注入(inject)到包装器的构造函数中,然后将其注入(inject)到服务构造函数中?

//code
public class ModelValidation : IModelValidation { 
public ModelValidation(ModelStateDictionary msd){...}
..
..
}

public class CustomerService{
public CustomerService(IModelValidation mv){...}
..
}

谢谢

最佳答案

根据您的评论,我特此修改我的答案:)

ModelStateDictionary 显然不是一个应该由容器解析的服务,而是应该在实例化时提供的数据。我们可以从以下事实看出这一点:ModelState 由每个 Controller 实例拥有,因此在“解析时”对容器不可用。

此外,每个 ModelValidation 实例将绑定(bind)到 ModelStateDictionary 实例,因此也被视为数据

在 Autofac 中,当数据必须传递给构造函数(可选地除了其他依赖项之外)时,我们必须使用工厂委托(delegate)。这些委托(delegate)将处理传递给构造函数的依赖关系和数据。 Autofac 的好处是这些委托(delegate)可以自动生成。

我提出以下解决方案:

由于 ModelValidation 和 CustomerService 都需要在其构造函数中提供数据,因此我们需要两个工厂委托(delegate)(注意:参数名称必须与其相应构造函数中的名称匹配):

public delegate IModelValidation ModelValidationFactory(ModelStateDictionary msd);
public delegate CustomerService CustomerServiceFactory(ModelStateDictionary msd);

由于您的 Controller 不应该知道这些委托(delegate)来自哪里,因此它们应该作为依赖项传递给 Controller ​​构造函数:

public class EditCustomerController : Controller
{
    private readonly CustomerService _customerService;

    public EditCustomerController(CustomerServiceFactory customerServiceFactory
        /*, ...any other dependencies required by the controller */
          )
    {
        _customerService = customerServiceFactory(this.ModelState);
    }

}

CustomerService 应该有一个与此类似的构造函数(可以选择在 ServiceBase 类中处理其中的一些内容):

public class CustomerService
{
    private readonly IModelValidation _modelValidation;

    public CustomerService(ModelStateDictionary msd,
              ModelValidationFactory modelValidationFactory)
    {
        _modelValidation = modelValidationFactory(msd);
    }

为了实现这一点,我们需要像这样构建容器:

var builder = new ContainerBuilder();

builder.Register<ModelValidation>().As<IModelValidation>().FactoryScoped();
builder.Register<CustomerService>().FactoryScoped();

builder.RegisterGeneratedFactory<ModelValidationFactory>();
builder.RegisterGeneratedFactory<CustomerServiceFactory>();

builder.Register<EditCustomerController>().FactoryScoped();

因此,当 Controller 被解析时(例如使用 the MvcIntegration module 时),工厂委托(delegate)将被注入(inject)到 Controller 和服务中。

更新:要进一步减少所需的代码,您可以将 CustomerServiceFactory 替换为我所描述的通用工厂委托(delegate) here .

关于asp.net-mvc - 如何使用 Autofac 将 Controller 的 ModelState 传递给我的服务构造函数?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/1818539/

相关文章:

c# - 如何从 NopCommerce v3.5 的设置表加载记录

asp.net-mvc - 是否可以配置 Autofac 以与 ASP.NET MVC 和 ASP.NET Web Api 一起使用

c# - Presenter 的依赖注入(inject)

asp.net-mvc - 窗口更新破坏了 MVC 应用程序

c# - 全局否定并使大小写不敏感

c# - 如何使用包含其他模型列表的模型创建下拉列表?

.net - ASP.NET MVC-使用Controller相应地设置主视图

inversion-of-control - Autofac - 如何从单例中解析 ISomething 的 Func,其中 ISomething 是 InstancePerHttpRequest

singleton - Autofac SingleInstance无法正常工作

c# - 如何提高返回到 asp.net mvc 中的 View 和输出的包含 5000 个对象的列表的性能?