Mam problemy z projektem MVC4, który frustrująco działa poprawnie na jednym komputerze (VS 2012), ale nie na drugim (VS 2010).Bezkontrowersyjny kontroler Konstruktor Autofac
(Mam nadzieję, że sprzeczne wersje VS nie są problemem, ale projekt pierwotnie pochodził z komputera VS2010, zrobiłem trochę pracy w 2012 roku, a teraz próbuję go przywrócić w 2010 roku.)
dostaję „Upewnij się, że kontroler ma bez parametrów konstruktora publicznego” błąd, ale uważam, że mój kontroler ma domyślną:
public class HomeController : AuthorizedControllerBase
{
public ViewResult Index()
{
return View();
}
}
Kod, który zgłasza błąd jest w moim ControllerFactory:
public class ControllerFactory : DefaultControllerFactory
{
private readonly IStateProvider _sessionStateProvider;
public ControllerFactory(IStateProvider aStateProvider)
{
_sessionStateProvider = aStateProvider;
}
public override IController CreateController
(System.Web.Routing.RequestContext requestContext, string controllerName)
{
IController controller = base.CreateController(requestContext, controllerName);
if (controller is BaseController)
{
var baseController = (BaseController)controller; // ***This line***
baseController.SessionData = _sessionStateProvider;
}
return controller;
}
}
Widziałem pytanie podobny do tego, w którym realizator interfejs nie miał konstruktora publicznego, ale ponownie, myślę, że kopalnia ma domyślną:
public class SessionStateProvider : IStateProvider
{
public object this[string key]
{
get
{
return HttpContext.Current.Session[key];
}
set
{
HttpContext.Current.Session[key] = value;
}
}
public void Remove(string key)
{
HttpContext.Current.Session.Remove(key);
}
}
Na podstawie odpowiedzi na inne pytania i stacktrace, jestem zaglądanie w problemy Autofac. Ja po prostu nie Install-Package Autofac
i mają najnowszą (3.0.2), w ramach projektu, a StackTrace wygląda następująco:
InnerException: Autofac.Core.DependencyResolutionException
Message=An exception was thrown while executing a resolve operation. See the InnerException for details. ---> Common Language Runtime detected an invalid program. (See inner exception for details.)
Source=Autofac
StackTrace:
at Autofac.Core.Resolving.ResolveOperation.Execute(IComponentRegistration registration, IEnumerable`1 parameters)
at Autofac.Core.Lifetime.LifetimeScope.ResolveComponent(IComponentRegistration registration, IEnumerable`1 parameters)
at Autofac.ResolutionExtensions.TryResolveService(IComponentContext context, Service service, IEnumerable`1 parameters, Object& instance)
at Autofac.ResolutionExtensions.ResolveOptionalService(IComponentContext context, Service service, IEnumerable`1 parameters)
at Autofac.ResolutionExtensions.ResolveOptional(IComponentContext context, Type serviceType, IEnumerable`1 parameters)
at Autofac.ResolutionExtensions.ResolveOptional(IComponentContext context, Type serviceType)
at Autofac.Integration.Mvc.AutofacDependencyResolver.GetService(Type serviceType)
at System.Web.Mvc.DefaultControllerFactory.DefaultControllerActivator.Create(RequestContext requestContext, Type controllerType)
InnerException: System.InvalidProgramException
Message=Common Language Runtime detected an invalid program.
Source=Autofac
StackTrace:
at Autofac.Core.Activators.Reflection.ConstructorParameterBinding..ctor(ConstructorInfo ci, IEnumerable`1 availableParameters, IComponentContext context)
at Autofac.Core.Activators.Reflection.ReflectionActivator.<>c__DisplayClass5.<GetConstructorBindings>b__4(ConstructorInfo ci)
at System.Linq.Enumerable.WhereSelectArrayIterator`2.MoveNext()
at System.Linq.Enumerable.WhereEnumerableIterator`1.MoveNext()
at System.Linq.Buffer`1..ctor(IEnumerable`1 source)
at System.Linq.Enumerable.ToArray[TSource](IEnumerable`1 source)
at Autofac.Core.Activators.Reflection.ReflectionActivator.ActivateInstance(IComponentContext context, IEnumerable`1 parameters)
at Autofac.Core.Resolving.InstanceLookup.Activate(IEnumerable`1 parameters)
at Autofac.Core.Resolving.InstanceLookup.Execute()
at Autofac.Core.Resolving.ResolveOperation.GetOrCreateInstance(ISharingLifetimeScope currentOperationScope, IComponentRegistration registration, IEnumerable`1 parameters)
at Autofac.Core.Resolving.InstanceLookup.ResolveComponent(IComponentRegistration registration, IEnumerable`1 parameters)
at Autofac.Core.Registration.ExternalRegistrySource.<>c__DisplayClass8.<RegistrationsFor>b__3(IComponentContext c, IEnumerable`1 p)
at Autofac.Core.Activators.Delegate.DelegateActivator.ActivateInstance(IComponentContext context, IEnumerable`1 parameters)
at Autofac.Core.Resolving.InstanceLookup.Activate(IEnumerable`1 parameters)
at Autofac.Core.Resolving.InstanceLookup.Execute()
at Autofac.Core.Resolving.ResolveOperation.GetOrCreateInstance(ISharingLifetimeScope currentOperationScope, IComponentRegistration registration, IEnumerable`1 parameters)
at Autofac.Core.Resolving.ResolveOperation.ResolveComponent(IComponentRegistration registration, IEnumerable`1 parameters)
at Autofac.Core.Resolving.ResolveOperation.Execute(IComponentRegistration registration, IEnumerable`1 parameters)
Dzieje się tak, mimo że ja rzeczywiście rejestracji IStateProvider tak: builder.Register(context => new SessionStateProvider()).As<IStateProvider>();
w ContainerBuilder.BuildContainer()
. W Global.asax ja również zarejestrować ControllerFactory:
protected void Application_Start()
{
Container = ContainerBuilder.BuildContainer();
var autofacDependencyResolver = new AutofacDependencyResolver(Container);
DependencyResolver.SetResolver(autofacDependencyResolver);
ControllerBuilder.Current.SetControllerFactory(new ControllerFactory(Container.Resolve<IStateProvider>()));
Application_Start_MVC();
}
Nie jestem pewien, co następne możliwe kroki dla próbuje rozwiązać ten problem (jestem droga z mojej głębokości parsowania z StackTrace Autofac), a ja Doceniam każdą pomoc.
VS2010 jest wyposażony w .net 4.0, ale z vs2012 .net 4.5 więc różnicy wersji ramy powoduje problem nie visual studio. Możesz spróbować zainstalować .net 4.5 na maszynie vs2010 lub możesz spróbować użyć starszej wersji Autofac jak 2.6, aby sprawdzić, czy działa w obu środowiskach. – nemesv
'InvalidProgramException' - wydaje się być błędem .NET Framework, gdy Autofac próbuje zbudować resolver. –
@nemesv Możesz dodać pakiet Microsoft Bcl, aby uzyskać dostęp do większości funkcji 4.5 w wersji 4.0. (Ale uważajcie, mogą zrobić bałagan, gdy używacie kontroli źródła) –