Search code examples
c#simple-injector

Custom IHttpControllerActivator for MvcControllers


Is there any way to register a custom IHttpControllerActivator for my Mvc controllers registered in simple injector, in a similar fashion to what can be done with Web API?

As soon as I run DependencyResolver.SetResolver(new SimpleInjectorDependencyResolver(container));, simple injector hooks in to my third party controllers as well, which I would like to avoid.


Solution

  • Based on Steven's suggestions in the comments, I came up with the following:

    public class MvcControllerFactory : DefaultControllerFactory
    {
        private readonly Container _container;
        private readonly IControllerFactory _original;
    
        public MvcControllerFactory(
            Container container, IControllerFactory original)
        {
            _container = container;
            _original = original;
        }
    
        protected override IController GetControllerInstance(
            RequestContext requestContext, Type controllerType)
        {
            if (controllerType == null)
            {
                return null;
            }
    
            if (controllerType == typeof(MyMvcController))
            {
                return (IController)_container.GetInstance(controllerType);
            }
    
            var controllerName = requestContext.RouteData.GetRequiredString("controller");
            if (!string.IsNullOrEmpty(controllerName))
            {
                return _original.CreateController(requestContext, controllerName);
            }
    
            return (IController) Activator.CreateInstance(controllerType);
        }
    }
    

    In my app start:

    var original = ControllerBuilder.Current.GetControllerFactory();
    var controllerFactory = new MvcControllerFactory(container, original);
    ControllerBuilder.Current.SetControllerFactory(controllerFactory);