So what’s Ninject. Ninject is a lightweight dependency injection framework for .NET applications. … and what is it good for (absolutely nothing?)? Ehm, not at all!
The simplest use case would be following scenario:
For example your design declares a singleton class. Normally you would code something like that:
public sealed class TheManager { static TheManager instance=null; static readonly object padlock = new object(); TheManager() { } public static TheManager Instance { get { lock (padlock) { if (instance==null) { instance = new TheManager(); } return instance; } } } }
Then you would get an instance of TheManager like that:
TheManager myManager = TheManager.Instance()
Okay, now we will use Ninject for our singleton pattern.
If you use Ninject you need not to add code for locking down your class to achieve a singleton behavior. You only have to tell Ninject that the class type should be tied to some implementation, in our example to itself. Furthermore, you have to setup the – what they call – Activation Behavior. In our Example it is,…. yes the InSingletonScope.
Ninject distinguishes between 4 (build-in) scopes:
Transient | .InTransientScope() |
A new instance of the type will be created each time one is requested. (This is the default scope) |
Singleton | .InSingletonScope() |
Only a single instance of the type will be created, and the same instance will be returned for each subsequent request. |
Thread | .InThreadScope() |
One instance of the type will be created per thread. |
Request | .InRequestScope() |
One instance of the type will be created per web request, and will be destroyed when the request ends. |
The first step would be to create a new NinjectModule which will hold the bindings.
public class MainModule : NinjectModule { public override void Load() { Bind<TheManager>().ToSelf().InSingletonScope(); } }
Our TheManager class looks like that:
public class TheManager { public TheManager() { } public DoManage() { System.Console.WriteLine("Resistance is futile"); } }
Now we can use our TheManager class as a singleton.
The simplest use would be if you ask the Ninject kernel for the TheManager class
class Program { static void Main(string[] args) { IKernel kernel = new StandardKernel(new MainModule()); TheManager myManager = kernel.Get<TheManager>(); } }
Whenever you call the Ninject kernel for the TheManager type implementation you will get a reference to the same instance.
But Ninjects magic can do a lot more cooler stuff for you.
Let’s suppose you have another class TheBoss which should use TheManager. And you want that if you instantiate the TheBoss it should automatically have a TheManager.
Then you could use the [Inject] Attribut. Whenever you use this Attribut Ninject will search his binding “tables” for an implementation which suits to the request context respectively to the bindings.
For example you can use the Property Injection feature. Here we annotate the myManager property with [Inject] . So if we create an instance of TheBoss we also get myManager automatically resolved.
public class TheBoss { [Inject] TheManager myManager { get; set;} public TheBoss() { } }