一种方便快捷的服务注册方案
前言#
随着dotnet的发展,DependencyInjection已经成为基础库的一部分,现在我们的很多新型应用程序很自然地应用了DependencyInjection功能。应用功能越多,往往服务类型数量也随着增加,如果依靠手写代码一个服务一个服务地进行注册则非常麻烦。如果使用特性标记服务,在运行时反射扫描服务并注册服务,不但会增加服务的启动时间,同时在AOT裁剪环境下服务类型由于没有显式的被使用而编译时默认被裁剪掉,从而表现为没有可注册的服务。
方案设计#
Annotation + SourceGenerator一种理解的方案,它仍然使用特性来标记服务,不同的是它在编译时使用SourceGenerator技术收集程序集里标记的服务类型,然后在集程序集里增加向DependencyInjection注册所有标记的服务的扩展方法代码。
经过SourceGenerator之后,和手写代码一个服务一个服务的注册的效果是完全一样的,最终程序在运行时,不再需要反射程序集扫描服务类型,启动速度会更快一丢丢。同时由于这些服务类型都是显式的被调用,所以也适用于AOT裁剪的项目环境,不再担心服务类型默认被裁剪掉。
方案实现#
DependencyInjection.Annotation 这是我对上述方案的一种实现,它开源在github上,支持一个实现对应一种或(最)多(6)种服务类型,使用方式也非常简单。
1 nuget引用#
<PackageReference Include="DependencyInjection.Annotation" Version="1.0.0" />
2 服务标记#
// 服务类型为MyService自身
[Service(ServiceLifetime.Singleton)]
class MyService
{
}
// 服务类型为IMyService1
[Service(ServiceLifetime.Singleton, typeof(IMyService1))]
class MyService : IMyService1
{
}
// 服务类型为IMyService1和IMyService2
[Service(ServiceLifetime.Singleton, typeof(IMyService1), typeof(IMyService2))]
class MyService : IMyService1, IMyService2, IDisposable
{
}
3 服务注册#
builder.Services.Add{AssemblyName}();
其中{AssemblyName}为包含服务的程序集名。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· DeepSeek 开源周回顾「GitHub 热点速览」
· 物流快递公司核心技术能力-地址解析分单基础技术分享
· .NET 10首个预览版发布:重大改进与新特性概览!
· AI与.NET技术实操系列(二):开始使用ML.NET
· 单线程的Redis速度为什么快?