Generally, if we create a .NET core web application using Visual Studio or dotnet CLI, the template already has Startup class. This class contains all basic setup, ready to use for using many different services.
So, in this article, let’s try to setup a demo console application to use dependency injection. That might help us understand the internals of how does it work.
Create a console application (let’s say DIConsoleDemo) using dotnet CLI or using the visual studio. Then add reference of the Microsoft.Extensions.Hosting NuGet package to the project.
Set of Interfaces
We are going to create an interface
IGetCreatedTime, which has a method
GetCreatedTime. The idea is to have a class which implements this interface (indirectly, wait for next step) and returns a
DateTime object, representing the time at which the current object was created.
To better understand the concept of singleton, scoped and transient service lifetimes discussed in previous post, let’s create three more interfaces:
Each one of the above three interfaces should implement the original interface
IGetCreatedTime and they will not contain any extra methods. All these 4 interfaces are shown in the below code snippet.
The implementation class is simple. It will implement three interfaces corresponding to three lifetimes. The class will capture the current date time in the constructor and will hold it in the
readonly field. The
GetCreatedTime method from the interface should return the
The concrete class is shown in the code snippet below:
This is a class where the constructor expects the three objects:
- first implementing
- second implementing
- third one implementing
Then there is a method invoke, which just invokes
GetCreatedTime method on each of the objects and prints the output as shown in below snippet.
For dependency injection, there are three important interfaces:
- IHost, this is the class which exposes the property of
- IServiceCollection, the collection where we can register details about service interface, its concrete implementation and the lifetime of the service, typically while the application is bootstrapping.
- IServiceProvider, which acts as container responsible for creating/maintaining/disposing the services registered using IServiceCollection
This is where the Nuget package is going to help. The CreateDefaultBuilder method creates an IHostBuilder instance with the default binder settings. ConfigureServices method provides the instance of IServiceCollection (services parameter) which we have used to register three interfaces. So each of the interface creates object of same class, but the lifetime of the object created is different.
As this is console application, it is not like web application and that’s why there is always going to be a single scope. But to simulate multiple scopes we have added a call to IServiceProvider.CreateScope() which creates a new scope.
For every scope, we invoke the invoker object’s method two times and the creation time of every object is printed to help us understand how the objects are getting used.
Run and Verify
Run the application and you should be able to see the output as shown below:
So, we have successfully demonstrated how the service lifetime works. I hope you find this demo useful. Let me know your thoughts.