服务的生命周期定义了服务实例的存在时间。它是否存在于应用程序的生命周期中?每个请求都创建了一个新实例吗?中间还有一些东西,如后面所述。
将服务注册为单例总是返回相同的实例,将服务注册为瞬态,每次注入服务时都会返回一个新对象。还有更多的选择,有更多的问题需要考虑。下面的示例将显示生命周期的特性和问题。该示例还用服务实现了IDisposable接口,因此可以看到这是如何处理的。
示例ServicesLifetime使用以下NuGet包和名称空间:
包
Microsoft.Extensions.DependencyInjection
名称空间
System
Microsoft.Extensions.DependencyInjection
为了方便地区分不同的实例,每个实例化的服务都指定了一个不同的号码。这个号码是由共享服务创建的。这个共享服务定义了一个简单的接口INumberService,返回一个号码:
public interface INumberService
{
int GetNumber();
}
INumberService的实现总是在GetNumber方法中返回一个新号码。该服务注册为一个单例,其号码在其他服务之间共享。
public class NumberService : INumberService
{
private int _number = 0;
public int GetNumber() => Interlocked.Increment(ref _number);
}
下面要介绍的其他服务由接口协议IServiceA、IServiceB、IServiceC等使用相应的方法A、B、C定义。下面的代码片段显示了IService的协定:
public interface IServiceA
{
void A();
}
在ServiceA的实现中,构造函数需要注入INumberService。通过这个服务,检索号码,将其分配给私有字段_n。在构造函数、方法A,以及实现IDisposable接口的Dispose方法中,写入控制台输出,因此可以看到生命周期信息:
public class ServiceA:IServiceA,IDisposable
{
private int _n;
public ServiceA(INumberService numberService)
{
_n = numberService.GetNumber();
Console.WriteLine($"ctor {nameof(ServiceA)},{_n}");
}
public void A() => Console.WriteLine($"{nameof(A)},{_n}");
public void Dispose() => Console.WriteLine($"disposing {nameof(ServiceA)},{_n}");
}
除了服务之外,还实现了控制器ControllerX。ControllerX要求构造函数注入三个服务:IServiceA、IServiceB和INumberService。在方法M中,调用了两个注入的服务。同时,构造函数和Dispose信息写入控制台:
public class ControllerX : IDisposable
{
private readonly IServiceA _serviceA;
private readonly IServiceB _serviceB;
private readonly int _n;
private int _countm = 0;
public ControllerX(IServiceA serviceA,IServiceB serviceB,INumberService numberService)
{
_n = numberService.GetNumber();
Console.WriteLine($"ctor {nameof(ControllerX)},{_n}");
_serviceA = serviceA;
_serviceB = serviceB;
}
public void M()
{
Console.WriteLine($"invoked {nameof(M)} for hte {++_countm}. time");
_serviceA.A();
_serviceB.B();
}
public void Dispose() => Console.WriteLine($"dis