AutoMapper将源属性映射到内部目标对象

时间:2018-06-25 16:12:37

标签: automapper

我有一个源类:

class Source {
    public string Name;
    public string Field1;
    public string Field2;
}

和两个目标类别:

class Destination {
    public string Name;
    public FieldsDto Fields;
}

class FieldsDto {
    public string Field1;
    public string FieldTwo;
}

如何将Source.Field1映射到Destination.Fields.Field1并将Source.Field2映射到Destination.Fields.FieldTwo

该代码不起作用;它会抛出一个错误,说Custom configuration for members is only supported for top-level individ ual members on a type1

Mapper.Initialize(cfg => {
    cfg.CreateMap<Source, Destination>()
        .ForMember(dest => dest.Fields.Field1, opt => opt.Mapfrom(src => src.Field1)
        .ForMember(dest => dest.Fields.FieldTwo, opt => opt.Mapfrom(src => src.Field2);
});

1 个答案:

答案 0 :(得分:1)

如注释中所述,为了映射嵌套的属性,您将需要使用ForPath而不是ForMember。因此完整的配置可能如下所示:

Mapper.Initialize(cfg =>
{
    cfg.CreateMap<Source, Destination>()
        .ForMember(dest => dest.Name, opt => opt.MapFrom(s => s.Name))
        .ForPath(dest => dest.Fields.Field1, opt => opt.MapFrom(src => src.Field1))
        .ForPath(dest => dest.Fields.FieldTwo, opt => opt.MapFrom(src => src.Field2));
});

如果您想使用成员名称作为字符串动态地执行此操作(就像我在聊天中学到的那样,看起来像您想做的事情),那么您将无法轻松使用ForPath,因为需要仅包含成员表达式的lambda表达式。

您可以 可以为嵌套成员访问动态创建一个lambda表达式。如果您进行搜索,我敢肯定您会在这里找到足够的示例,以了解如何创建此类lambda表达式。

另一种方法是将映射分为单独的类型。因此,您可以直接映射嵌套对象,而不是直接映射到Destination的嵌套属性。像这样:

Mapper.Initialize(cfg =>
{
    cfg.CreateMap<Source, FieldsDto>()
        .ForMember("Field1", opt => opt.MapFrom("Field1"))
        .ForMember("FieldTwo", opt => opt.MapFrom("Field2"));
    cfg.CreateMap<Source, Destination>()
        .ForMember(dest => dest.Name, opt => opt.MapFrom(s => s.Name))
        .ForMember(dest => dest.Fields, opt => opt.MapFrom(s => Mapper.Map<FieldsDto>(s)));
});