You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用AutoMapper为泛型类OverridableValue<T>创建通用映射?

问题:AutoMapper中为泛型类OverridableValue配置通用映射

我有一个泛型类OverridableValue<T>,用于表示可手动覆盖的值(包含T类型的Value属性和一个标记是否为手动设置的布尔值)。该类用于内部模型中,而API的DTO只需保存值,无需关注是否为手动设置。例如以下类:

public class Test
{
    public OverridableValue<string> Prop1 { get; set; }
    public OverridableValue<int> Prop2 { get; set; }
}

public class TestDTO
{
    public string Prop1 { get; set; }
    public int Prop2 { get; set; }
}

目前我可以通过以下方式创建Test与TestDTO的映射:

CreateMap<OverridableValue<string>, string>().ConvertUsing(o => o.Value);
CreateMap<OverridableValue<int>, int>().ConvertUsing(o => o.Value);
CreateMap<Test, TestDTO>();

但我不想为OverridableValue的每个泛型用法都添加一行映射配置,希望创建一个适用于所有泛型实例的通用映射,类似:

CreateMap<OverridableValue<T>, T>().ConvertUsing(o => o.Value);

请问是否有实现这种通用映射的方法?


解决方案

AutoMapper支持通过泛型类型定义配置全局通用映射,无需为每个具体的OverridableValue<T>重复编写配置,具体实现有两种方式:

方法一:基于泛型类型定义+通用转换器(推荐)

直接针对OverridableValue<>的泛型类型定义创建映射,搭配通用转换器实现全局规则:

// 在AutoMapper配置中添加以下代码
var overridableGenericType = typeof(OverridableValue<>);
// 为所有OverridableValue<T>到T的转换配置通用规则
CreateMap(overridableGenericType, overridableGenericType.GetGenericArguments()[0])
    .ConvertUsing(typeof(OverridableValueConverter<>));

// 定义通用转换器类
public class OverridableValueConverter<T> : ITypeConverter<OverridableValue<T>, T>
{
    public T Convert(OverridableValue<T> source, T destination, ResolutionContext context)
    {
        return source.Value;
    }
}

配置完成后,所有OverridableValue<T>类型的属性在映射到T类型时,都会自动应用这个转换规则,包括Test到TestDTO的映射会自动生效。

方法二:通过ForAllMaps自动识别配置

如果需要更灵活的属性级控制,可以用ForAllMaps遍历所有映射规则,自动识别OverridableValue<T>类型的属性并配置映射:

var config = new MapperConfiguration(cfg =>
{
    cfg.ForAllMaps((map, exp) =>
    {
        foreach (var sourceProp in map.SourceType.GetProperties())
        {
            var propType = sourceProp.PropertyType;
            // 判断属性是否为OverridableValue<T>的泛型实例
            if (propType.IsGenericType && propType.GetGenericTypeDefinition() == typeof(OverridableValue<>))
            {
                var targetProp = map.DestinationType.GetProperty(sourceProp.Name);
                if (targetProp != null)
                {
                    // 配置该属性映射到对应的Value值
                    exp.ForMember(targetProp.Name, opt =>
                        opt.MapFrom(src => sourceProp.GetValue(src)?.GetType().GetProperty("Value").GetValue(sourceProp.GetValue(src))));
                }
            }
        }
    });

    // 添加具体的类映射
    cfg.CreateMap<Test, TestDTO>();
});

内容的提问来源于stack exchange,提问作者DorBS

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.26 21:12:38