¿Cuál es la diferencia entre los servicios.AddTransient, service.AddScoped y service.AddSingleton métodos en ASP.NET Core?

Quiero implementar la dependency injection en Asp.Net Core . Entonces, después de agregar estos códigos al método ConfigureServices , ambas formas funcionan.

¿Cuál es la diferencia entre los servicios. Los métodos AddTransient y service.AddScope son Asp.Net Core?

public void ConfigureServices(IServiceCollection services) { // Add framework services. // Add application services. services.AddTransient(); services.AddScoped(); } 

Para mayor aclaración, este ejemplo de asp.net docs muestra la diferencia:

Para demostrar la diferencia entre estas opciones de vida y de registro, considere una interfaz simple que represente una o más tareas como una operación con un identificador único, OperationId . Dependiendo de cómo configuremos la duración de este servicio, el contenedor proporcionará las mismas o diferentes instancias del servicio para la clase solicitante. Para aclarar qué tiempo de vida se está solicitando, crearemos un tipo de opción de por vida:

 using System; namespace DependencyInjectionSample.Interfaces { public interface IOperation { Guid OperationId { get; } } public interface IOperationTransient : IOperation { } public interface IOperationScoped : IOperation { } public interface IOperationSingleton : IOperation { } public interface IOperationSingletonInstance : IOperation { } } 

Implementamos estas interfaces usando una sola clase, Operation , que acepta un Guid en su constructor, o utiliza un nuevo Guid si no se proporciona.

A continuación, en ConfigureServices , cada tipo se agrega al contenedor de acuerdo con su duración definida:

 services.AddTransient(); services.AddScoped(); services.AddSingleton(); services.AddSingleton(new Operation(Guid.Empty)); services.AddTransient(); 

Tenga en cuenta que el servicio IOperationSingletonInstance está utilizando una instancia específica con un ID conocido de Guid.Empty por lo que quedará claro cuando este tipo esté en uso. También registramos un OperationService que depende de cada uno de los otros tipos de Operation , de modo que quede claro en una solicitud si este servicio obtiene la misma instancia que el controlador, o una nueva, para cada tipo de operación. Todo lo que hace este servicio es exponer sus dependencias como propiedades, por lo que se pueden mostrar en la vista.

 using DependencyInjectionSample.Interfaces; namespace DependencyInjectionSample.Services { public class OperationService { public IOperationTransient TransientOperation { get; } public IOperationScoped ScopedOperation { get; } public IOperationSingleton SingletonOperation { get; } public IOperationSingletonInstance SingletonInstanceOperation { get; } public OperationService(IOperationTransient transientOperation, IOperationScoped scopedOperation, IOperationSingleton singletonOperation, IOperationSingletonInstance instanceOperation) { TransientOperation = transientOperation; ScopedOperation = scopedOperation; SingletonOperation = singletonOperation; SingletonInstanceOperation = instanceOperation; } } } 

Para demostrar la vida útil del objeto dentro y entre solicitudes individuales separadas a la aplicación, la muestra incluye un OperationsController que solicita cada tipo de tipo IOperation así como también un OperationService . La acción Index muestra todos los valores OperationId del controlador y del servicio.

 using DependencyInjectionSample.Interfaces; using DependencyInjectionSample.Services; using Microsoft.AspNetCore.Mvc; namespace DependencyInjectionSample.Controllers { public class OperationsController : Controller { private readonly OperationService _operationService; private readonly IOperationTransient _transientOperation; private readonly IOperationScoped _scopedOperation; private readonly IOperationSingleton _singletonOperation; private readonly IOperationSingletonInstance _singletonInstanceOperation; public OperationsController(OperationService operationService, IOperationTransient transientOperation, IOperationScoped scopedOperation, IOperationSingleton singletonOperation, IOperationSingletonInstance singletonInstanceOperation) { _operationService = operationService; _transientOperation = transientOperation; _scopedOperation = scopedOperation; _singletonOperation = singletonOperation; _singletonInstanceOperation = singletonInstanceOperation; } public IActionResult Index() { // viewbag contains controller-requested services ViewBag.Transient = _transientOperation; ViewBag.Scoped = _scopedOperation; ViewBag.Singleton = _singletonOperation; ViewBag.SingletonInstance = _singletonInstanceOperation; // operation service has its own requested services ViewBag.Service = _operationService; return View(); } } } 

Ahora se realizan dos solicitudes por separado a esta acción del controlador: Primera solicitud

Segundo requisito

Observe cuál de los valores de OperationId varía dentro de una solicitud, y entre las solicitudes.

  • Los objetos transitorios son siempre diferentes; se proporciona una nueva instancia a cada controlador y cada servicio.

  • Los objetos delimitados son los mismos dentro de una solicitud, pero diferentes en diferentes solicitudes

  • Los objetos Singleton son los mismos para cada objeto y cada solicitud (independientemente de si se proporciona una instancia en ConfigureServices )

En la dependency injection de dotnet hay 3 vidas principales:

Singleton que crea una sola instancia en toda la aplicación. Crea la instancia por primera vez y reutiliza el mismo objeto en todas las llamadas.

Los servicios con scope de por vida se crean una vez por solicitud dentro del scope. Es equivalente a Singleton en el scope actual. p.ej. en MVC crea 1 instancia por cada solicitud http pero usa la misma instancia en las otras llamadas dentro de la misma solicitud web.

Los servicios de duración transitoria se crean cada vez que se solicitan. Esta vida útil funciona mejor para servicios livianos y apátridas.

Aquí puedes encontrar y ejemplos para ver la diferencia:

http://dotnetliberty.com/index.php/2015/10/15/asp-net-5-mvc6-dependency-injection-in-6-steps/

https://codewala.net/2015/04/30/your-dependency-injection-ready-asp-net-asp-net-5/

y este es el enlace a la documentación oficial:

https://docs.asp.net/en/latest/fundamentals/dependency-injection.html#service-lifetimes-and-registration-options

  • Singleton es una instancia única durante el tiempo de vida del dominio de la aplicación.
  • Scoped es una instancia única para la duración de la solicitud de ámbito, lo que significa por solicitud HTTP en ASP.NET.
  • Transient es una instancia única por solicitud de código .

Normalmente, la solicitud del código debe hacerse a través de un parámetro constructor, como en

 public MyConsumingClass(IDependency dependency) 

Quería señalar en la respuesta de @ akazemis que “servicios” en el contexto de DI no implica servicios RESTful; los servicios son implementaciones de dependencias que proporcionan funcionalidad.

Transient, Scoped y Singleton definen el proceso de creación de objetos en ASP.NET MVC core DI cuando se deben inyectar múltiples objetos del mismo tipo. En caso de que sea nuevo en la inyección de Dependencia, puede ver este video del DI IOC

Puede ver el código del controlador a continuación en el que he solicitado dos instancias de “IDal” en el constructor. Transient, Scoped y Singleton definen si la misma instancia se inyectará en “_dal” y “_dal1” o diferente.

 public class CustomerController : Controller { IDal dal = null; public CustomerController(IDal _dal ,IDal _dal1) { dal = _dal; // DI of MVC core // inversion of control } } 

Transitorio: en instancias transitorias de objetos nuevos, se inyectará en una única solicitud y respuesta. A continuación se muestra una imagen instantánea donde se muestran los valores GUID.

enter image description here

Alcance: – En el mismo objeto, la instancia del objeto se inyectará en una sola solicitud y respuesta.

enter image description here

Singleton: – En Singleton, el mismo objeto se inyectará en todas las solicitudes y respuestas. En este caso, se creará una instancia global del objeto.

A continuación se muestra un diagtwig simple que explica los aspectos fundamentales anteriores visualmente.

Imagen MVC DI

La imagen de arriba fue dibujada por el equipo de SBSS cuando estaba tomando capacitación ASP.NET MVC en entrenamiento de Mumbai , muchas gracias al equipo de SBSS para crear la imagen de arriba.