簡體   English   中英

如何使用 Automapper 在目標 object 中保留集合的未映射屬性?

[英]How to preserve the not mapped properties of a collection in a destination object with Automapper?

初始情況:我有一個源和一個目標 object 並且都有一個Elements集合。 使用 Automapper I map 從源到目標 object。之后,我將信息添加到僅存在於目標 object( ItemNameItemNumber )上的屬性。 此外,我將信息添加到集合AssetElementDto中對象的屬性Text 之后,我調用mapper.Map(source_update, destination); 更新目的地 object。

問題:當我運行代碼時,更新后保留了ItemNameItemNumber的信息。 我該怎么做才能保留TextAssetElementDto信息?

using AutoMapper;
using System.Runtime.InteropServices;

public class Program
{
    static void Main(string[] arg)
    {
        var config = new MapperConfiguration(cfg =>
        {
            cfg.CreateMap<Source, Destination>().PreserveReferences();
            cfg.CreateMap<AssetElement, AssetElementDto>().PreserveReferences();
        });
        var mapper = new Mapper(config);

        var source = new Source()
        {
            Name = "Sinonis",
            Id = new Random().Next(),
            Elements = new List<AssetElement>
            {
                new(){ Id = 1},
                new(){ Id = 2}
            }
        };

        var destination = mapper.Map<Destination>(source);
        destination.ItemNumber = 42;
        destination.Elements.ForEach(e => e.Text ="Wow");

        destination.ItemName = "NPC21";

        var source_update = new Source()
        {
            Name = "Nindalf",
            Id = new Random().Next(),
            Elements = new List<AssetElement>
            {
                new(){ Id = 3},
                new(){ Id = 4}
            }
        };

        Console.WriteLine($"Before update is: {destination.Name} {destination.Id} {destination.ItemNumber} {destination.ItemName}");
        destination.Elements.ForEach(e => Console.WriteLine($" {e.Id} {e.Text}"));

        mapper.Map(source_update, destination);

        Console.WriteLine($"After update is : {destination.Name} {destination.Id} {destination.ItemNumber} {destination.ItemName}");
        destination.Elements.ForEach(e => Console.WriteLine($" {e.Id} {e.Text}"));
    }
}

#region Source

public class Source
{
    public string Name;
    public int Id;

    public List<AssetElement> Elements;

}

public class AssetElement
{
    public int Id;
}

#endregion

#region Destination

public class Destination
{
    public string Name;
    public int Id;

    public List<AssetElementDto> Elements;

    public int ItemNumber;
    public string ItemName;
}

public class AssetElementDto
{
    public string Text;
    public int Id;
}

#endregion

控制台 Output:

更新后Wow沒有保留。

Before update is: Sinonis 1643275093 42 NPC21
 1 Wow
 2 Wow
After update is : Nindalf 75522068 42 NPC21
 3 null
 4 null

感謝Lucian Bargaoanu提供的這個簡短而有力的提示。 這解決了我的問題。 請在下面的代碼中查看必要的更改。 這是 AutoMapper.Collection 的鏈接

using AutoMapper;
using AutoMapper.EquivalencyExpression; //add using

public class Program
{
    static void Main(string[] arg)
    {
        var config = new MapperConfiguration(cfg =>
        {
            cfg.AddCollectionMappers(); //add the collection mapper
            cfg.CreateMap<Source, Destination>();
            cfg.CreateMap<AssetElement, AssetElementDto>().EqualityComparison((odto, o) => odto.Id == o.Id); //add the equality compersion
        });
        var mapper = new Mapper(config);

        var source = new Source()
        {
            Name = "Sinonis",
            Id = new Random().Next(),
            Elements = new List<AssetElement>
            {
                new(){ Id = 1},
                new(){ Id = 2}
            }
        };

        var destination = mapper.Map<Destination>(source);
        destination.ItemNumber = 42;
        destination.ItemName = "NPC21";
        destination.Elements.ForEach(e => e.Text ="Wow");

       

        var source_update = new Source()
        {
            Name = "Nindalf",
            Id = new Random().Next(),
            Elements = new List<AssetElement>
            {
                new(){ Id = 1},//ID's need to be the same as before
                new(){ Id = 2}
            }
        };

        Console.WriteLine($"Before update is: {destination.Name} {destination.Id} {destination.ItemNumber} {destination.ItemName}");
        destination.Elements.ForEach(e => Console.WriteLine($" {e.Id} {e.Text}"));

        mapper.Map(source_update, destination);

        Console.WriteLine($"After update is : {destination.Name} {destination.Id} {destination.ItemNumber} {destination.ItemName}");
        destination.Elements.ForEach(e => Console.WriteLine($" {e.Id} {e.Text}"));
    }
}

#region Source

public class Source
{
    public string Name;
    public int Id;

    public List<AssetElement> Elements;

}

public class AssetElement
{
    public int Id;
}


#endregion

#region Destination

public class Destination
{
    public string Name;
    public int Id;

    public List<AssetElementDto> Elements;

    public int ItemNumber;
    public string ItemName;
}

public class AssetElementDto
{
    public string Text;
    public int Id;
}

#endregion

安慰:

更新后Wow保留在合集中。

Before update is: Sinonis 49772274 42 NPC21
 1 Wow
 2 Wow
After update is : Nindalf 236466397 42 NPC21
 1 Wow
 2 Wow

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM