【问题标题】:Autofac - Make sure that the controller has a parameterless public constructorAutofac - 确保控制器有一个无参数的公共构造函数
【发布时间】:2016-05-31 09:36:57
【问题描述】:

我知道之前有人问过并回答过 - 我问的原因是因为(我认为)我尝试了所有建议的解决方案,但仍然无法解决。

我有一个 ASP.NET Web API 2.0 项目。我安装了 AutofacAutofac.Mvc5Autofac.WebApi2 依赖项。当我尝试调用 API 控制器时,出现以下错误:

尝试创建类型为“MyController”的控制器时出错。确保控制器有一个无参数的公共构造函数。

在我的Global.asax 中,我有一个对IocConfig.Config() 的调用,我已将它放在App_Start 中:

public static class IocConfig
{
    public static void Config()
    {
        var builder = new ContainerBuilder();

        builder.RegisterType<MyLogger>().As<IMyLogger>();

        builder.RegisterApiControllers(Assembly.GetCallingAssembly());
        builder.RegisterWebApiFilterProvider(GlobalConfiguration.Configuration);

        WebApiApplication.Container = builder.Build();

        DependencyResolver.SetResolver(
            new AutofacDependencyResolver(WebApiApplication.Container));
        GlobalConfiguration.Configuration.DependencyResolver =
             new AutofacWebApiDependencyResolver(WebApiApplication.Container);
    }
}

这是MyController的构造函数:

public MyController(IMyLogger logger)

当我尝试调用它时,我得到关于构造函数的指定错误。我错过了什么?

【问题讨论】:

  • 解决了吗?我有相同的问题。我正在使用 Asp.Net Web api2.0

标签: c# asp.net autofac autofac-configuration


【解决方案1】:

我也遇到了这个错误,根本原因是控制器的依赖项之一没有在 Autofac 中正确注册。

InnerException 包含详细信息(在我的情况下,它是 Autofac.Core.DependencyResolutionException),而 ExceptionMessage 包含此依赖项的详细信息。大致如下:

“激活特定注册时出错...无法解析参数'XXXX'

【讨论】:

  • 这解决了它!内部异常包含了真正的问题,即缺少注册。
  • FWIW:如果您不知道哪个参数可能是由于构造函数不公开而导致的。在我的情况下,构造函数是内部的。将其切换为公开,一切正常。
  • 这为我指明了正确的方向。很棒的提示!
【解决方案2】:

检查this answer
它可以帮助我为 WebApi 控制器配置正确的 ContainerBuilder()

如果您在此处寻找此类错误的解决方案,您应该首先检查您的 DependencyResolver 配置。

我遇到了同样的问题,问题是我将 Autofac 代码示例用于 MVC 控制器而不是 API 的 ContainerBuilder() 对象。

我的代码用于注册两种类型的控制器(MVC 和 Api):

var builder = new ContainerBuilder();
builder.RegisterControllers(Assembly.GetExecutingAssembly()); //Register MVC Controllers
builder.RegisterApiControllers(Assembly.GetExecutingAssembly()); //Register WebApi Controllers
builder.RegisterType<Type>().As<IType>();

var container = builder.Build();

DependencyResolver.SetResolver(new AutofacDependencyResolver(container)); //Set the MVC DependencyResolver
GlobalConfiguration.Configuration.DependencyResolver = new AutofacWebApiDependencyResolver((IContainer)container); //Set the WebApi DependencyResolver

【讨论】:

  • 没想到这是答案,因为我错过了流水线。你能把它加到你的上面描述吗?
  • 如果您使用的是 ASP.Net Identity,这可能就是答案。
  • @neustart47 最后一行解决了我的问题,感谢您的输入。
【解决方案3】:

Assembly.GetCallingAssembly() 将返回调用程序集,而不是定义类型的程序集。

Assembly.GetCallingAssembly方法
返回调用当前执行方法的方法的程序集。

为了使其正常工作,您应该使用typeof(IocConfig).AssemblyAssembly.GetExecutingAssembly

【讨论】:

  • 我已经尝试过Assembly.GetExecutingAssembly 也尝试过你建议尝试typeof(IocConfig).Assembly - 仍然是同样的错误
【解决方案4】:

您可能缺少 WebApiConfig.cs 文件中的调用配置:

IocConfigurator.ConfigureDependencyInjection(config);

ConfigureDependencyInjection 可以是这样的:

public static void ConfigureDependencyInjection(HttpConfiguration config)
        {

            var builder = new ContainerBuilder();

            // Register your Web API controllers.
            builder.RegisterApiControllers(Assembly.GetExecutingAssembly());

            // OPTIONAL: Register the Autofac filter provider.
            builder.RegisterWebApiFilterProvider(config);

            // OPTIONAL: Register the Autofac model binder provider.
            builder.RegisterWebApiModelBinderProvider();

            // Set the dependency resolver to be Autofac.
            var container = builder.Build();
            config.DependencyResolver = new AutofacWebApiDependencyResolver(container);

        }

【讨论】:

  • 这可能不被推荐,但它在遗留项目中就像一个魅力。我的限制是我不允许更改此项目的初始设置方式,因此我无法通过启动文件使其正常工作。谢谢!
【解决方案5】:

我认为您缺少在应用启动代码中注册 autofac。

使用这个:

protected void Application_Start()
{
    IocConfig.Config();
    AreaRegistration.RegisterAllAreas();
    FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);
    RouteConfig.RegisterRoutes(RouteTable.Routes);
   BundleConfig.RegisterBundles(BundleTable.Bundles);
}

更多详情请参考此博客http://www.codeproject.com/Articles/808894/IoC-in-ASP-NET-MVC-using-Autofac

【讨论】:

  • 正如我在原始问题中所写的那样“在我的 Global.asax 中,我调用了 IocConfig.Config() 并将其放入内部” - 它甚至会破坏配置本身 - 所以它肯定会运行。
  • 它应该在 Application_Start 中调用,因为它会在应用程序域的生命周期内被调用一次。
  • 它被调用一次。如Application_Start 中所述。此外,将代码从它自己的方法之外直接移动到Application_Start 仍然不起作用。
【解决方案6】:

打开你的 ServiceModule 文件

注册控制器中提到的接口和服务名称。

示例如下:-

builder.RegisterType().As();

【讨论】:

    猜你喜欢
    • 2018-07-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-04-28
    • 2016-06-20
    • 1970-01-01
    • 2023-04-04
    • 1970-01-01
    相关资源
    最近更新 更多