Injecting NServiceBus into ASP.NET WebApi

Posted on March 16, 2012

2


This is just an update of David Boike’s excellent blog post on injecting NServiceBus into ASP.NET MVC 3. I take no credit, but simply followed David’s instructions and made them work for WebApi because I needed it myself. I would recommend you read his blog first then use the following code samples for injecting NServiceBus into ASP.NET WebApi.

New classes

    public class NSBHttpControllerActivator : IHttpControllerActivator
    {
        public IHttpController Create(HttpControllerContext controllerContext, Type controllerType)
        {
            return GlobalConfiguration.Configuration.ServiceResolver        
                 .GetService(controllerType) as IHttpController;
        }
    }

    public class NServiceBusResolverAdapter : IDependencyResolver
    {
        private IBuilder builder;

        public NServiceBusResolverAdapter(IBuilder builder)
        {
            this.builder = builder;
        }

        public object GetService(Type serviceType)
        {
            if(typeof(IHttpController).IsAssignableFrom(serviceType))
            {
                return builder.Build(serviceType);
            }
            
            return null;
        }

        public IEnumerable GetServices(Type serviceType)
        {
            if (typeof(IHttpController).IsAssignableFrom(serviceType))
            {
                return builder.BuildAll(serviceType);
            }

            return null;
        }
    }

    public static class ConfigureWebApi
    {
        public static Configure ForWebApi(this Configure configure)
        {
            // Register our http controller activator with NSB
            configure.Configurer.RegisterSingleton(typeof(IHttpControllerActivator),
                new NSBHttpControllerActivator());

            // Find every http controller class so that we can register it
            var controllers = Configure.TypesToScan
                .Where(t => typeof(IHttpController).IsAssignableFrom(t));

            // Register each http controller class with the NServiceBus container
            foreach (Type type in controllers)
                configure.Configurer.ConfigureComponent(type, ComponentCallModelEnum.Singlecall);

            // Set the WebApi dependency resolver to use our resolver
            GlobalConfiguration.Configuration.ServiceResolver.SetResolver(new NServiceBusResolverAdapter(configure.Builder));
            
            // Required by the fluent configuration semantics
            return configure;
        }
    }

Application Start

        protected void Application_Start()
        {
            AreaRegistration.RegisterAllAreas();

            // Use LocalDB for Entity Framework by default
            Database.DefaultConnectionFactory = new SqlConnectionFactory("Data Source=(localdb)\v11.0; Integrated Security=True; MultipleActiveResultSets=True");

            RegisterGlobalFilters(GlobalFilters.Filters);
            RegisterRoutes(RouteTable.Routes);

            BundleTable.Bundles.RegisterTemplateBundles();
            
            Configure.WithWeb()
                .DefaultBuilder()
                .ForWebApi()   // <------ here is the line that registers everything
                .Log4Net()
                .XmlSerializer()
                .MsmqTransport()
                    .IsTransactional(false)
                    .PurgeOnStartup(false)
                .UnicastBus()
                    .ImpersonateSender(false)
                .CreateBus()
                .Start();
        }

An alternative to doing the above would be to self-host the WebApi in an NServiceBus host process. Whatever suits your architecture best.

That’s all…

Advertisements
Tagged: ,
Posted in: NServiceBus, WebApi