Using Ninject for dependency injection

Possibly save 4 hours of your time: If you follow best practice, you may already know about dependency injection. It has many benefits but I won’t talk about it here. You can wikipedia it. I often build ASP.NET MVC and WebAPI applications and in the controller you may create different helper or service class to get your model. Instead of new ‘ing a class, you can create your controller constructor to take in those helper or service class as parameters. Then you can access it directly to retrieve your model. A big benefit is the ability to write unit tests for your controller layer only and mock the helper or service class.

In the example below the controller gets injected an instance of yourService at runtime by Ninject. There are different scopes. By default, it is in Transient scope and it means a new instance is always created. You can read more on different type of scopes here.

Example of api controller:


namespace YourProject.Web.Controllers
{
 [RoutePrefix("api")]
 public class SomeNameController : ApiController
 {
 private readonly IYourService yourService;
 public SomeNameController(IYourService yourService)
 {
 this.yourService = yourService;
 }

 [Route("getproduct/{productId}")]
 [HttpGet]
 public SomeViewModel Get(string productId)
 {
 try
 {
 var model = new SomeViewModel();
 model.Values = yourService.GetValues();
 return model;
 }
 catch (Exception ex)
 {

throw new HttpException(500, ex.Message);
 }
 }
 }

}

I will now talk about how to set up Ninject. Open your web solution. I installed the following from Visual Studio >> Tools >> NuGet Package Manager >> Manage NuGet Packages for solution:

  • Ninject (3.3.3)
  • Ninject.MVC5 (3.3.0)
  • Ninject.Web.Common (3.3.0)
  • Ninject.Web.WebApi (3.3.0)
  • WebActivatorEx (2.2.0)

 

Second, you need to add this static class for NinjectWebCommon.cs.


using System;
using Ninject;
using Ninject.Web.WebApi;
using Ninject.Web.Common;
using System.Web.Http;

[assembly: WebActivatorEx.PreApplicationStartMethod(typeof(YourProjectName.Web.App_Start.NinjectWebCommon), "Start")]
[assembly: WebActivatorEx.ApplicationShutdownMethodAttribute(typeof(YourProjectName.Web.App_Start.NinjectWebCommon), "Stop")]

namespace YourProjectName.Web.App_Start
{
 public static class NinjectWebCommon
 {
 private static readonly Bootstrapper bootstrapper = new Bootstrapper();

/// <summary>
/// Starts the application
/// </summary>
 public static void Start()
 {
 bootstrapper.Initialize(CreateKernel);
 }

/// <summary>
/// Stops the application.
/// </summary>
 public static void Stop()
 {
 bootstrapper.ShutDown();
 }

/// <summary>
/// Creates the kernel that will manage your application.
/// </summary>
/// <returns>The created kernel.</returns>
 private static IKernel CreateKernel()
 {
 var kernel = new StandardKernel();
 try
 {
kernel.Bind<Func<IKernel>>().ToMethod(ctx => () => new Bootstrapper().Kernel);

RegisterServices(kernel);

// Install our Ninject-based IDependencyResolver into the Web API config
 GlobalConfiguration.Configuration.DependencyResolver = new NinjectDependencyResolver(kernel);

return kernel;
 }
 catch
 {
 kernel.Dispose();
 throw;
 }
 }

 /// <summary>
/// Load your modules or register your services here!
/// </summary>
/// <param name="kernel">The kernel.</param>
 private static void RegisterServices(IKernel kernel)
 {
kernel.Bind<IYourService>().To<YourService>();
 }
 }
}

When running the app I got the following error. This means your Ninject is not setup properly.

Error: 

An error occurred when trying to create a controller of type YourTypeName. Make sure that the controller has a parameterless public constructor.

Type ‘YourTypeName’ does not have a default constructor

Mastering Ninject for Dependency Injection

Advertisements

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google+ photo

You are commenting using your Google+ account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s