上一篇有一个读者,有疑问,如何自动化注册Dto
我开篇,做了一个自动化注册的
public sealed class AutoInjectAttribute : Attribute { public Type SourceType { get; } public Type TargetType { get; } public AutoInjectAttribute(Type sourceType, Type targetType) { SourceType = sourceType; TargetType = targetType; } }
增加了一个特性,在Dto上面打上,参数1是源类型,参数2是Dto类型
增加一个工厂类保存自动转换的类型
public class AutoInjectFactory { public List<(Type,Type)> ConvertList { get; } = new List<(Type, Type)>(); public void AddAssemblys(params Assembly[] assemblys) { foreach (var assembly in assemblys) { var atributes = assembly.GetTypes() .Where(_type => _type.GetCustomAttribute<AutoInjectAttribute>() != null) .Select(_type => _type.GetCustomAttribute<AutoInjectAttribute>()); foreach (var atribute in atributes) { ConvertList.Add((atribute.SourceType, atribute.TargetType)); } } } }
在原来的AddAutoMapper上找到修改的代码段
public static IServiceCollection AddAutoMapper(this IServiceCollection service) { ...略 service.TryAddSingleton(serviceProvider => { var mapperConfigurationExpression = serviceProvider.GetRequiredService<MapperConfigurationExpression>(); var instance = new MapperConfiguration(mapperConfigurationExpression); instance.AssertConfigurationIsValid(); return instance; }); ...略 return service; }
改为
public static IServiceCollection AddAutoMapper(this IServiceCollection service) { ...略 service.TryAddSingleton(serviceProvider => { var mapperConfigurationExpression = serviceProvider.GetRequiredService<MapperConfigurationExpression>(); var factory = serviceProvider.GetRequiredService<AutoInjectFactory>(); foreach (var (sourceType,targetType) in factory.ConvertList) { mapperConfigurationExpression.CreateMap(sourceType, targetType); } var instance = new MapperConfiguration(mapperConfigurationExpression); instance.AssertConfigurationIsValid(); return instance; }); ...略 return service; }
增加一组扩展方法
public static class AutoMapperExtension { ...略 public static void UseAutoInject(this IApplicationBuilder applicationBuilder, params Assembly[] assemblys) { var factory = applicationBuilder.ApplicationServices.GetRequiredService<AutoInjectFactory>(); factory.AddAssemblys(assemblys); } }
在Startup.Configure方法内调用一下
看看测试
增加一个测试控制器
执行结果