如何在AutoMapper的ConstructUsing调用中获取HttpContext.User.Claims的值
解决方案
方案1:直接在ConstructUsing中获取IHttpContextAccessor取值
无复用需求时优先使用该方案,实现最简单:
- 首先在服务容器中注册
IHttpContextAccessor:
// Program.cs (.NET 6+) builder.Services.AddHttpContextAccessor();
- 修改AutoMapper映射配置,从
ConstructUsing的ResolutionContext中获取服务提取Claim值:
CreateMap<SourceType, DestinationType>() .ConstructUsing((src, context) => { var httpAccessor = context.ServiceProvider.GetRequiredService<IHttpContextAccessor>(); var secretId = httpAccessor.HttpContext.User.Claims.First(c => c.Type == "SecretId").Value; return DestinationType.Factory.Create( src.SomeProperty, secretId // 其余工厂入参 ); });
方案2:复用现有SecretIdResolver逻辑
如果需要复用已写好的值解析器逻辑,可以直接从容器取出解析器调用:
- 先将
SecretIdResolver注册到依赖注入容器:
// Program.cs (.NET 6+) builder.Services.AddScoped<SecretIdResolver>();
- 修改映射配置,在
ConstructUsing中调用解析器:
CreateMap<SourceType, DestinationType>() .ConstructUsing((src, context) => { var resolver = context.ServiceProvider.GetRequiredService<SecretIdResolver>(); // 构造阶段目标对象还未生成,dest相关参数直接传null即可 var secretId = resolver.Resolve(src, null, null, context); return DestinationType.Factory.Create( src.SomeProperty, secretId // 其余工厂入参 ); });
注意事项
- 以上方案仅适用于通过官方集成方法
AddAutoMapper()注册AutoMapper的场景,保证ResolutionContext可以正确访问DI容器。 - 不要在Profile的构造函数中直接注入
IHttpContextAccessor,Profile为单例生命周期,直接注入会导致生命周期不匹配问题,必须通过ResolutionContext在映射执行时动态获取服务。 - 如果
ServiceProvider下找不到GetRequiredService方法,需要引入Microsoft.Extensions.DependencyInjection命名空间。
内容的提问来源于stack exchange,提问作者treywheeler
相关产品推荐
相关产品推荐

