自动映射器配置以正常映射基本字典值和成员

问题描述 投票:0回答:1

我有以下课程。

public class FieldValue
{
    public string Field { get; set; }
    public object Value { get; set; }
}

public class FieldValues
{
    public FieldValue[] Values { get; set; }
}

public static class FieldValuesExtensions
{
    public static IDictionary<string, object> ToDictionary(this FieldValues self)
    {
        return self.Values.ToDictionary(v => v.Field, v => v.Value);
    }
}

public class SourceClass : FieldValues
{
    public int Id { get; set; }
    public string Name { get; set; }
}

public class DestinationClassA
{
    public int Id { get; set; }
    public string Field1 { get; set; }
    public string Field2 { get; set; }
}

public class DestinationClassB
{
    public string Name { get; set; }
    public string Field2 { get; set; }
    public string Field3 { get; set; }
}

SourceClass
源自
FieldValues
并且有自己的字段。
DestinationClassX
类型仅由字段组成。

我需要从

SourceClass
映射到
DestinationClassX
,如下所示:

public class TestClass
{
    public static void Test(IMapper mapper)
    {
        // create a SourceClass object
        SourceClass source = new() {
            Id = 123,
            Name = "Foo",
            Values = new FieldValue[] {
                new() { Field = "Field1", Value = "Value1" },
                new() { Field = "Field2", Value = "Value2" },
                new() { Field = "Field3", Value = "Value3" },
                new() { Field = "Field4", Value = "Value4" }
            }
        };

        // how do we setup mapping configuration to achieve the following?

        // map to DestinationClassA
        DestinationClassA destinationA = mapper.Map<SourceClass, DestinationAClass>(source);
        // destinationA.Id == 123;
        // destinationA.Field1 == "Value1";
        // destinationA.Field2 == "Value2";

        // map to DestinationClassB
        DestinationClassB destinationB = mapper.Map<SourceClass, DestinationBClass>(source);
        // destinationB.Name == "Foo";
        // destinationB.Field2 == "Value2";
        // destinationB.Field3 == "Value3";
    }
}

我需要设置自动映射器映射以从

SourceClass
映射到
DestinationClassX
,以便任何匹配的目标字段都从以下位置映射:

  1. 来自

    SourceClass
    基础的任何匹配字段/值
    FieldValues

  2. 以及

    SourceClass
    本身的任何匹配成员正常。

我知道 Automapper 可以自动从动态对象以及 IDictionary 进行映射。例如,如果我有一个包含

DestinationClassX
成员的课程:

public class DestinationClassWithA
{
    public DestinationClassA A { get; set; }
}

具有以下映射:

CreateMap<SourceClass, DestinationClassA>(); // map 1

CreateMap<SourceClass, DestinationClassWithA>() 
    .ForMember(dst => dst.A, opt => opt.MapFrom(src => src.ToDictionary())); // map 2

Destination.A
Field1
Field2
按照地图 2 进行填充,但地图 1 中的
Id
设置为
null
。如果我注释掉地图 2,地图 1 就可以工作,但我当然不会得到字典条目。

我不知道如何将字典地图(地图2)合并到地图1中。

CreateMap<SourceClass, DestinationClassA>()
    // what goes here? 

CreateMap<SourceClass, DestinationClassB>()
    // what goes here? 
c# automapper
1个回答
0
投票

您需要分两步进行映射。

AfterMap
对此有帮助。您还可以使用映射继承来重用派生映射中的配置。

    cfg.CreateMap<FieldValues, object>().AfterMap((s,d,c)=>c.Mapper.Map(s.ToDictionary(), d));
    cfg.CreateMap<SourceClass, DestinationClassA>(MemberList.None).IncludeBase<FieldValues, object>();
    cfg.CreateMap<SourceClass, DestinationClassB>(MemberList.None).IncludeBase<FieldValues, object>();
© www.soinside.com 2019 - 2024. All rights reserved.