Dependency Injection And Service Lifetime in ASP.NET Core

Introduction

Dependency injection is a technique of providing a dependent object from outside rather than the class creating using the new keyword.

Pros

  1. It increased modularity
  2. It improves testability
  3. Centralize place to provide the dependency
  4. Decouple system

ASP.NET Core supports the dependency injection (DI) software design pattern, which is a technique for achieving Inversion of Control (IoC) between classes and their dependencies.

  • Constructor Injection: The most used approach of injecting dependencies into a class by passing them as parameters in the constructor.
  • Method Injection: Injecting dependencies into a method as parameters.
  • Property Injection: Setting properties of a class with the required dependencies.

When we register the dependency to DI Container (IServiceCollection) we need to specify the lifetime of that dependency.

Service Lifetime

The service lifetime controls how long an object will live after it has been created by the container. The lifetime can be created by using the below method on the IServiceColletion when registering.

  1. Transient: Services are created each time they are requested.
    Example: With transient tea makers, it's like giving each customer a different tea. They enjoy a unique tea experience as a new tea maker arrives for each order and serving.
  2. Scoped: Services are created once per request.
    Example: Scoped tea makers in a teashop are like having one tea maker assigned to each table or group, providing the same type of tea to everyone within that group. When a new group arrives, they receive their dedicated tea maker.
  3. Singleton: Services are created once for the lifetime of the application.
    Example: In a teashop with a singleton tea maker, it's like having a legendary tea master who serves the same tea to every customer. This tea master is always there, remembers all orders, and consistently provides the same tea to everyone.

Now let's jump into the code to elaborate on this concept in more detail.

TeaService

public class TeaService : ITeaService
{
        private readonly int _randomId ;
        private readonly Dictionary<int, string> _teaDictionary = new()
        {
            { 1, "Normal Tea ☕️" },
            { 2, "Lemon Tea ☕️" },
            { 3, "Green Tea ☕️" },
            { 4, "Masala Chai ☕️" },
            { 5, "Ginger Tea ☕️" }
        };
 public TeaService()
 {
      _randomId = new Random().Next(1, 5);
  } 
  public string GetTea()
   {
      return _teaDictionary[_randomId];

    }
}
public interface ITeaService
{
        string GetTea();
}

RestaurantService: which injects TeaService.

public class RestaurantService : IRestaurantService
{
        private readonly ITeaService _teaService;
        public RestaurantService(ITeaService teaService)
        {
            _teaService = teaService;
        }

        public string GetTea()
        {
            return _teaService.GetTea();
        }
}
public interface IRestaurantService
{
     string GetTea();
 }

Tea Controller: which is injecting TeaService and RestaurantService.

[Route("api/[controller]")]
[ApiController]
public class TeaController : ControllerBase
{
  private readonly ITeaService _teaService;
  private readonly IRestaurantService _restaurantService;

  public TeaController(ITeaService teaService, 
   IRestaurantService restaurantService)
  {
      _teaService = teaService;
      _restaurantService = restaurantService;
   }

   [HttpGet]
   public IActionResult Get()
   {
      var tea = _teaService.GetTea();
      var teaFromRestra = _restaurantService.GetTea();
      return Ok($"From TeaService : {tea} 
               \nFrom RestaurantService : {teaFromRestra}");
    }       
}

Register services to DI Container.

a. Transient

// Add the below line to configure service in Statup.cs
services.AddTransient<ITeaService, TeaService>();
services.AddTransient<IRestaurantService, RestaurantService>();

Output

b. Scoped

// Add the below line to configure service in Statup.cs
services.AddScoped<ITeaService, TeaService>();
services.AddScoped<IRestaurantService, RestaurantService>();

Output

c: Singleton

// Add the below line to configure service in Statup.cs
services.AddSingleton<ITeaService, TeaService>();
services.AddSingleton<IRestaurantService, RestaurantService>();

Output

Github commit ID for more details: https://github.com/rahulsdotnet/LearnWebAPI/commit/2797b92e2fb7cca6a986c2c181b244ba42d484c5

Hope this article finds you well. Thanks for reading this.


Similar Articles