Dependency Injection in .Net helps developing decoupled applications.
In the software development world of today the emphasis is on applying good design principles and patterns.Applying software principles while developing an application results in less overhead in the long term. After all the maintenance phase is one of the most expensive phases in the software life-cycle.
One of the things to keep in mind while developing any application today is to create a loosely coupled application design.Creating loosely coupled applications results in applications which are easier to maintain and extend.The requirement changes are frequent today than ever before ,where we follow Agile practices.So creating extensible application architecture is not something which we can overlook when developing a new application.
Inversion of Control (IoC) is a principle which helps in creating loosely coupled applications.It is just a principle and does not specify the implementation.
In Inversion of control the application flow is inverted.Normally we call the framework API for different tasks.”But in Inversion of control the framework knows about the objects being used in our application and calls them when required”.This call or invocation happens at run time which results in loose coupling between the objects.
IoC says that a component should not depend directly upon any another component, it should rather depend upon an abstraction.
In our application if we have two classes which depend upon each other then we may design them as depicted in the below diagram
So if we redesign the application according to the IoC principle then our design can be depicted by the following diagram
So Class A now depends upon an abstraction such as an interface or an abstract class.
Some of the examples of design patterns which implement IoC are
- dependency injection
- event loops
- service locator
- callbacks
Lets see what is dependency injection and how we can implement Dependency Injection in .Net.
In any application different components or classes work together to achieve a common functionality.We will take the example of Student Information System.We have a class called Student which provides a feature to mail the student details.For sending the mails the Student class relies on another class called EmailProviderA (EmailProviderA is just another email provider) which provides the mail functionality.As segregating the application functionality into different components is a good practice so using a separate class for sending a mail is the correct design.Currently the class is defined as
class Student { private EmailProviderA _emailProviderA ; public Student() { _emailProviderA =new EmailProviderA(); _emailProviderA.Subject = this.Name; } public void SendMail() { _emailProviderA.SendMail(); } }
As you can see above the Student class is creating an object of EmailProviderA in its constructor.This may appear to be perfect today but unfortunately it can create problem.Tomorrow if we want to send mails using any other EmailProvider then we will have to create an object of different class(instead of EmailProviderA) in the constructor of Student class and therefore would need to change our code accordingly.
We can resolve this problem using dependency injection which is an implementation of Inversion of Control principle. According to Dependency injection the dependency of a class should be injected or passed by the calling code and the class should not be dependent upon the implementation but on an abstraction.So analyzing our Student class in terms of dependency injection we find the following
1) Our class should not depend upon implementation but on an abstraction.
Student class violates this as it depends upon the EmailProviderA concrete class.
2) The specific implementation details of the abstraction should not be decided by the class but by the client code or the consumer of the class.
Student class violates this as it itself creates an instance of the EmailProviderA class.
Lets see how we can modify the class so that it implements dependency injection.
Here we will implement Dependency Injection using C#.
We introduce IEmailProvider interface and make our EmailProviderA class implement this interface.We change the type of reference field in the Student class from EmailProviderA class to the IEmailProvider interface.
interface IEmailProvider { bool SendMail(); string Subject{get;set;} } class Student { private IEmailProvider _emailProvider ; public Student() { _emailProvider=new EmailProviderA(); _emailProvider.Subject = this.Name; } public void SendMail() { _emailProvider.SendMail(); } }
Though we have changed the type of the field to interface but still in our constructor the object of concrete class is being created.So we will remove the code to create the EmailProviderA class from the constructor.In the following code we have removed the code to create an object of EmailProviderA from the constructor and are passing the interface reference as a constructor argument.
class Student { private IEmailProvider _emailProvider ; public Student(IEmailProvider emailProvider) { _emailProvider= emailProvider; _emailProvider.Subject = this.Name; } public void SendMail() { _emailProvider.SendMail(); }
As we need a reference to EmailProviderA class on which our Student class depends so we are passing this as a constructor argument.The client code is responsible for supplying the EmailProviderA reference as a constructor argument,the Student class has no dependency on the EmailProviderA class now.
One obvious advantage of this is if we can easily swap the EmailProviderA class with any other class in our application.The only requirement is that the new class should implement the IEmailProvider interface.We just need to pass the reference to this new class in the Student class constructor.The Student class will remain unchanged.
What we have implemented above is an example of constructor injection.Dependency injection can be implemented using two approaches.
- Constructor injection Dependencies are passed as arguments using class constructor.
- Property injection Dependencies are passed as properties.
We should use constructor injection when we have required dependencies.Let’s say we have a class which updates some records in the database and need a connection object to perform this.So we should inject the dependency using constructor here.So when an object of a class could not be created without passing the dependencies,in this case connection object, constructor injection should be used.
On the other hand property injection should be used if we have many optional dependencies.
We have just seen how to implement constructor injection.To implement the property injection we just need to add a property which returns an abstraction,an interface , and we can set the value of the property in the calling code.So taking the same example of the Student class we can introduce a new property as
public IEmailProvider EmailProviderA { set { this._emailProvider = value; } }
Instead of creating the dependencies ourselves we can use IoC containers which automatically inject the dependencies.We need to register our dependencies with the container and it is automatically resolved.Some of the common IoC containers which we can use to inject dependencies in .NET are
- Castle Windsor
- StructureMap
- Unity
- Ninject
Implementing Dependency injection in .net application has the following advantages
- Loose coupling between the application components makes the application more maintainable and extensible
- Components are easy to unit test
- Components can be resued
Pravakar Mishra says
The article is really helpful and informative. I must go through all the articles in this website. Its really a good one for the beginners.
Also, it helps, if you bring up some scenarios, which you might have come across and wanted others also to gain knowledge on that.
ashish shukla says
Thanks for the suggestion!
I am glad to know that you are finding the articles helpful.
I will try to cover more scenarios in future.
Madhu says
After going thru this article got the clear understanding about dependency injection which I never had better understanding. Thanks for the good write up. Expecting more articles….
ashish says
Thanks!. I am glad that you got better understanding about dependency injection.
Mateen Kadwaikar says
I am working on ASP.NET Web API and I have around 4 Controllers and 5 common methods. I am using Unity.WebAPI DI.
I wanted to know should I have to pass every Interface through constructor.
For e.g public ABCController(ICDEd customer,IdValidation validation)
{
if (customer == null) throw new ArgumentNullException(nameof(customer));
_customer = customer;
if (validation == null) throw new ArgumentNullException(nameof(validation));
_validation = validation;
}
I am using entity framework how can I make that class as loose coupling.
Thanks
ashish says
Hi Mateen,
As I understand from the above scenario ,you could use the following approach:
1. Use the Unity container for injecting the constructor dependencies.I think you are already doing this.
2. For the class references which are common across the different controllers ,you can use property injection.If
there is any other common functionality as well then you can move it to a base class.
You can also remove the dependency on Entity Framework in your application.For example to remove the dependency on the DbContext class Set () where TEntity : class;
you can implement an Interface as:
public interface IDbContext {
DbSet
int SaveChanges();
}
Then instead of directly referencing the DbContext you reference IDbContext in your application.
Let me know if this solves your problem.
nithish reddy says
This article was very useful for .net developers !
thanks for posting !
can you explain unity container concepts with a small example .