asp.net - simple - globalconfiguration configuration dependencyresolver getservice
Inyector simple: no se ha definido ningún constructor sin parámetros para este objeto (2)
Tengo un nuevo MVC Web Project en el que utilizo MVC y WebApi. He configurado Simple Injector (versión 2.5.2 desde nuGet) usando el siguiente código en mi archivo global
// Register Injectors
SimpleInjectorConfig.Register();
En mi archivo SimpleInjectorConfig.cs tengo
public class SimpleInjectorConfig
{
public static void Register() {
// Create the container as usual.
Container container = new Container();
// services
container.Register<IService, MyService>();
// data
container.Register<IRepository, MyRepository>();
// Register your types, for instance using the RegisterWebApiRequest
// extension from the integration package:
container.RegisterMvcControllers(
System.Reflection.Assembly.GetExecutingAssembly());
container.RegisterMvcAttributeFilterProvider();
// This is an extension method from the integration package.
container.RegisterWebApiControllers(GlobalConfiguration.Configuration);
// verify its all ok
container.Verify();
// add dependency
GlobalConfiguration.Configuration.DependencyResolver =
new SimpleInjectorWebApiDependencyResolver(container);
}
}
Ahora tengo 2 controladores, 1 es un controlador webApi y 1 es un controlador MVC normal.
Mi controlador WebApi funciona bien y se ve así
public class MyApiController : ApiController
{
private IService _service;
public MyApiController(IService service)
{
_service = service;
}
/// <summary>
/// GET api/<controller>/5
/// </summary>
/// <param name="id"></param>
/// <returns></returns>
public IHttpActionResult Get(int id)
{
// i get my entity here and return it
EntityObject myEntity = _service.Get(id);
return Ok(myEntity);
}
}
Como dije, el código anterior funciona bien, puedo ejecutar la url y devuelve lo que esperaría.
Ahora tengo mi controlador de vista MVC, que se ve muy similar al anterior, aquí está
public class MyController : Controller
{
private IService _service;
public MyController(IService service)
{
_service = service;
}
public ActionResult Index()
{
return Search();
}
// Company/Search
public ActionResult Search()
{
return View();
}
}
Ahora no puedo entender en absoluto por qué sigo recibiendo el siguiente error. No puedo agregar un contructor público ya que causa un error con SimpleInjector.
No parameterless constructor defined for this object.
Description: An unhandled exception occurred during the execution of the current web request. Please review the stack trace for more information about the error and where it originated in the code.
Exception Details: System.MissingMethodException: No parameterless constructor defined for this object.
Source Error:
An unhandled exception was generated during the execution of the current web request. Information regarding the origin and location of the exception can be identified using the exception stack trace below.
Stack Trace:
[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) +66
System.Web.Mvc.DefaultControllerActivator.Create(RequestContext requestContext, Type controllerType) +110
[InvalidOperationException: An error occurred when trying to create a controller of type ''my.project.Web.Controllers.MyController''. Make sure that the controller has a parameterless public constructor.]
System.Web.Mvc.DefaultControllerActivator.Create(RequestContext requestContext, Type controllerType) +247
System.Web.Mvc.DefaultControllerFactory.GetControllerInstance(RequestContext requestContext, Type controllerType) +438
System.Web.Mvc.DefaultControllerFactory.CreateController(RequestContext requestContext, String controllerName) +257
System.Web.Mvc.MvcHandler.ProcessRequestInit(HttpContextBase httpContext, IController& controller, IControllerFactory& factory) +328
System.Web.Mvc.MvcHandler.BeginProcessRequest(HttpContextBase httpContext, AsyncCallback callback, Object state) +157
System.Web.Mvc.MvcHandler.BeginProcessRequest(HttpContext httpContext, AsyncCallback callback, Object state) +88
System.Web.Mvc.MvcHandler.System.Web.IHttpAsyncHandler.BeginProcessRequest(HttpContext context, AsyncCallback cb, Object extraData) +50
System.Web.CallHandlerExecutionStep.System.Web.HttpApplication.IExecutionStep.Execute() +301
System.Web.HttpApplication.ExecuteStep(IExecutionStep step, Boolean& completedSynchronously) +155
Si alguien pudiera señalarme en la dirección correcta, sería genial.
El método SetResolver descrito anteriormente se compilará pero cuando se ejecute la aplicación, obtendrá un error ArgumentException: "Información adicional: el tipo SimpleInjector.Integration.WebApi.SimpleInjectorWebApiDependencyResolver no parece implementar Microsoft.Practices.ServiceLocation.IServiceLocator".
Resolverá este problema configurando DependencyResolver en SimpleInjectorWebApiDependencyResolver y transfiéralo a su contenedor, como se muestra a continuación.
GlobalConfiguration.Configuration.DependencyResolver = new SimpleInjectorWebApiDependencyResolver(container);
La razón para obtener este error es porque le falta el siguiente registro (como se explica en la guía de integración de MVC ):
DependencyResolver.SetResolver(new SimpleInjectorDependencyResolver(container));
MVC y Web API tienen su propia abstracción para resolver dependencias (ambas llamadas ''resolución de dependencia''). Como no configuró el resolver para MVC, MVC usa el mecanismo de resolución predeterminado para crear controladores MVC, pero esto requiere que los controladores tengan un constructor predeterminado.
Llamar a DependencyResolver.SetResolver
resolverá el problema.