2012-09-24 14 views
3

有沒有一種方法可以在通過builder.RegisterControllers()在外部程序集中加載的控制器中啓用注入?當我在我的插件文件夾中複製完全相同的程序集時,我得到一個無參數的構造函數未找到錯誤。Autofac注入到加載了RegisterControllers的控制器()

// This doesnt work, parameterless constructor not found! 
var assemblies = new DirectoryInfo(
         HttpContext.Current.Server.MapPath("~/App_Plugins/")) 
       .GetFiles("*.dll") 
       .Select(r => Assembly.LoadFrom(r.FullName)).ToArray(); 

// This works, injection happens correctly on constructor 
var assemblies = new[] {typeof (MvcApplication).Assembly}; 

第二個會工作,而第一個會產生錯誤。我試圖manualy還註冊了 「外部」 的控制器,但仍是同樣的問題:

builder.RegisterAssemblyTypes(assemblies) 
     .Where(r => r.BaseType == typeof(Controller)) 
     .InstancePerHttpRequest(); 

我使用MVC 4

堆棧跟蹤的DefaultControllerFactory是這樣的:

No parameterless constructor defined for this object.

[MissingMethodException: No parameterless constructor defined for this object.] 
    System.RuntimeTypeHandle.CreateInstance(RuntimeType type, Boolean publicOnly, Boolean noCheck, Boolean& canBeCached, RuntimeMethodHandleInternal& ctor, Boolean& bNeedSecurityCheck) +0 
    System.RuntimeType.CreateInstanceSlow(Boolean publicOnly, Boolean skipCheckThis, Boolean fillCache, StackCrawlMark& stackMark) +113 
    System.RuntimeType.CreateInstanceDefaultCtor(Boolean publicOnly, Boolean skipCheckThis, Boolean fillCache, StackCrawlMark& stackMark) +232 
    System.Activator.CreateInstance(Type type, Boolean nonPublic) +83 
    System.Activator.CreateInstance(Type type) +6 
    System.Web.Mvc.DefaultControllerActivator.Create(RequestContext requestContext, Type controllerType) +55 

[InvalidOperationException: An error occurred when trying to create a controller of type 'TestProject.Controllers.HomeController'. Make sure that the controller has a parameterless public constructor.] 
    System.Web.Mvc.DefaultControllerActivator.Create(RequestContext requestContext, Type controllerType) +178 
    System.Web.Mvc.DefaultControllerFactory.GetControllerInstance(RequestContext requestContext, Type controllerType) +77 
    System.Web.Mvc.DefaultControllerFactory.CreateController(RequestContext requestContext, String controllerName) +66 
    System.Web.Mvc.MvcHandler.ProcessRequestInit(HttpContextBase httpContext, IController& controller, IControllerFactory& factory) +191 
    System.Web.Mvc.MvcHandler.BeginProcessRequest(HttpContextBase httpContext, AsyncCallback callback, Object state) +50 
    System.Web.Mvc.MvcHandler.BeginProcessRequest(HttpContext httpContext, AsyncCallback callback, Object state) +48 
    System.Web.Mvc.MvcHandler.System.Web.IHttpAsyncHandler.BeginProcessRequest(HttpContext context, AsyncCallback cb, Object extraData) +16 
    System.Web.CallHandlerExecutionStep.System.Web.HttpApplication.IExecutionStep.Execute() +301 
    System.Web.HttpApplication.ExecuteStep(IExecutionStep step, Boolean& completedSynchronously) +155 
+0

你解決了這個問題嗎? – zed

回答

0

我沒有看到Autofac參與堆棧跟蹤。如果Autofac不滿異常會看起來像:

[DependencyResolutionException: None of the constructors found with 'Public binding flags' on type 'SomeApp.WebApplication.Areas.Shared.Controllers.AccountController' can be invoked with the available services and parameters: 
Cannot resolve parameter 'SomeApp.WebApplication.Areas.Shared.Controllers.Slappy slappy' of constructor 'Void .ctor(SomeApp.Web.LoginService, SomeApp.Web.AccountMembership.IMembershipService, SomeApp.Infrastructure.Logging.ILog, SomeApp.WebApplication.Areas.Shared.Controllers.Slappy)'.] 
    Autofac.Core.Activators.Reflection.ReflectionActivator.ActivateInstance(IComponentContext context, IEnumerable`1 parameters) +377 
    Autofac.Core.Resolving.InstanceLookup.Activate(IEnumerable`1 parameters) +48 
    Autofac.Core.Resolving.InstanceLookup.Execute() +48 
    Autofac.Core.Resolving.ResolveOperation.GetOrCreateInstance(ISharingLifetimeScope currentOperationScope, IComponentRegistration registration, IEnumerable`1 parameters) +167 
    Autofac.Core.Resolving.ResolveOperation.Execute(IComponentRegistration registration, IEnumerable`1 parameters) +64 
    Autofac.Core.Lifetime.LifetimeScope.ResolveComponent(IComponentRegistration registration, IEnumerable`1 parameters) +163 
    Autofac.ResolutionExtensions.TryResolveService(IComponentContext context, Service service, IEnumerable`1 parameters, Object& instance) +70 
    Autofac.ResolutionExtensions.ResolveOptionalService(IComponentContext context, Service service, IEnumerable`1 parameters) +53 
    Autofac.Integration.Mvc.AutofacDependencyResolver.GetService(Type serviceType) +59 
    System.Web.Mvc.DefaultControllerActivator.Create(RequestContext requestContext, Type controllerType) +41 

[InvalidOperationException: An error occurred when trying to create a controller of type 'SomeApp.WebApplication.Areas.Shared.Controllers.AccountController'. Make sure that the controller has a parameterless public constructor.] 
    System.Web.Mvc.DefaultControllerActivator.Create(RequestContext requestContext, Type controllerType) +179 
    System.Web.Mvc.DefaultControllerFactory.GetControllerInstance(RequestContext requestContext, Type controllerType) +80 
    System.Web.Mvc.DefaultControllerFactory.CreateController(RequestContext requestContext, String controllerName) +74 
    System.Web.Mvc.MvcHandler.ProcessRequestInit(HttpContextBase httpContext, IController& controller, IControllerFactory& factory) +196 
    System.Web.Mvc.<>c__DisplayClass6.<BeginProcessRequest>b__2() +49 
    System.Web.Mvc.<>c__DisplayClassb`1.<ProcessInApplicationTrust>b__a() +13 
    System.Web.Mvc.SecurityUtil.<GetCallInAppTrustThunk>b__0(Action f) +7 
    System.Web.Mvc.SecurityUtil.ProcessInApplicationTrust(Action action) +22 
    System.Web.Mvc.SecurityUtil.ProcessInApplicationTrust(Func`1 func) +88 
    System.Web.Mvc.MvcHandler.BeginProcessRequest(HttpContextBase httpContext, AsyncCallback callback, Object state) +98 
    System.Web.Mvc.MvcHandler.BeginProcessRequest(HttpContext httpContext, AsyncCallback callback, Object state) +50 
    System.Web.Mvc.MvcHandler.System.Web.IHttpAsyncHandler.BeginProcessRequest(HttpContext context, AsyncCallback cb, Object extraData) +16 
    System.Web.CallHandlerExecutionStep.System.Web.HttpApplication.IExecutionStep.Execute() +301 
    System.Web.HttpApplication.ExecuteStep(IExecutionStep step, Boolean& completedSynchronously) +155 

驗證您正在設置DependencyResolver

DependencyResolver.SetResolver(new AutofacDependencyResolver(ApplicationContainer)); 
+0

感謝您的回覆。當autofac解析器返回null時,它將返回到Activator.CreateInstance()。 Autofac解決方案在傳遞與'typeof(MvcApplication).Assembly'完全相同的程序集時可以正常工作,這就是奇怪的部分。 –

+0

嗯,好的。那麼,我會檢查簡單的東西,比如設置斷點來驗證你的'assemblies'變量具有你所期望的值。然後展開'.Where(r => r.BaseType == typeof(Controller))',以便可以檢查比較的類型和結果。 –