.NET通用方法编写:实现适配任意泛型接口的服务注册逻辑
泛型服务注册通用方法实现
你可以将这段代码改写成基于IServiceCollection的扩展方法,通过传入泛型接口的定义类型来适配不同的泛型接口,具体实现如下:
原代码回顾
Assembly.GetExecutingAssembly() .GetTypes() .Where(item => item.GetInterfaces() .Where(i => i.IsGenericType) .Any(i => i.GetGenericTypeDefinition() == typeof(IRepository<>)) && !item.IsAbstract && !item.IsInterface) .ToList() .ForEach(assignedTypes => { var serviceType = assignedTypes.GetInterfaces().First(i => i.GetGenericTypeDefinition() == typeof(IRepository<>)); services.AddScoped(serviceType, assignedTypes); });
通用方法实现
public static class ServiceCollectionExtensions { public static void AddGenericServicesFromCurrentAssembly(this IServiceCollection services, Type genericInterfaceDefinition) { // 校验参数合法性:必须是泛型接口的定义(如 typeof(IRepository<>)) if (!genericInterfaceDefinition.IsGenericTypeDefinition || !genericInterfaceDefinition.IsInterface) { throw new ArgumentException("参数必须是泛型接口的定义类型,例如 typeof(IRepository<>)", nameof(genericInterfaceDefinition)); } Assembly.GetExecutingAssembly() .GetTypes() // 筛选条件:非抽象类、非接口,且实现了目标泛型接口 .Where(type => !type.IsAbstract && !type.IsInterface && type.GetInterfaces().Any(i => i.IsGenericType && i.GetGenericTypeDefinition() == genericInterfaceDefinition)) .ToList() .ForEach(implementationType => { // 获取对应的泛型接口类型 var serviceInterface = implementationType.GetInterfaces() .First(i => i.IsGenericType && i.GetGenericTypeDefinition() == genericInterfaceDefinition); // 注册为Scoped服务(可根据需求改为AddSingleton/AddTransient) services.AddScoped(serviceInterface, implementationType); }); } }
使用方式
在依赖注入配置中,直接传入目标泛型接口的定义类型即可:
// 注册所有实现IRepository<>的服务 services.AddGenericServicesFromCurrentAssembly(typeof(IRepository<>)); // 注册所有实现IService<>的服务 services.AddGenericServicesFromCurrentAssembly(typeof(IService<>));
关键说明
- 参数灵活性:通过
genericInterfaceDefinition参数替换硬编码的typeof(IRepository<>),支持任意泛型接口 - 合法性校验:增加参数校验,避免传入错误的类型(比如具体的泛型实例
IRepository<User>或非泛型接口) - 扩展性:如果需要支持从其他程序集扫描,可新增一个参数传入目标
Assembly,替换Assembly.GetExecutingAssembly() - 生命周期可调整:当前默认用
AddScoped,可根据需求改为AddSingleton或AddTransient,甚至新增参数指定生命周期
内容的提问来源于stack exchange,提问作者dr.Xis
相关产品推荐
相关产品推荐

