سؤال

I've updated AutoMapper to its version 2 and I've got a lot a problems with it now...

I've got a list of ItemToMap and all of these objects have got a reference to the same object Tag

When I try to map ItemToMap with ItemToMapDto, I've got this error:

AutoMapper.AutoMapperMappingException :

Mapping types: Tag -> TagDto DAL.Entities.Tag -> DTO.Objects.TagDto

Destination path: ItemToMap[][1].Tag.Tag

Source value: Entities.Tag ----> System.ArgumentException : An item with the same key has already been added.

Here's the mapping:

Mapper.CreateMap<ItemToMap, ItemToMapDto>();
Mapper.CreateMap<Tag, TagDto>();

Here's the unit test that highlights my problem:

var temp = new List<ItemToMap>();
var tag1 = this.RandomTag;
var length = 10;

for (int i = 0; i < length; i++)
{
    temp.Add(new ItemToMap()
    {
        Tag = tag1,
    });
}
var record = temp.ToArray();
var mapped = Mapper.Map<ItemToMap[], ItemToMapDto[]>(record);

What is the solution to have my mapping works? I'm looking for a global solution because the problem is spread all around the code...

EDIT 1:

The problem comes from the ctor below, if I comment the code of the ctor, everything works fine...

public class ItemToMapDto
{
    public ItemToMapDto()
    {
        /* If I comment the line below, all's fine... But it not the behaviour 
         * I want, I'd like to have a default value for the property... 
         */
        this.Tag = new TagDto() { Name = this.RandomText };
    }

    public string Name
    {
        get;
        set;
    }

    public TagDto Tag
    {
        get;
        set;
    }
}

EDIT 2:

Automapper is caching ResolutionContext to reuse already set resolvers. In other words, it loops through the mappers and takes the one that return true on the call of IsMatch. To know whether this ResolutionContext is cached, it checks if the destination property is already set and the hash code of the context. Because the destination is set in the Ctor, Automapper considers this is not cached and therefore, it calls the uncached resolver. The latter resolver will cache but it fails because the hash code already exists in the Dictionary used as cache repository

هل كانت مفيدة؟

المحلول

This is a bug. The fix will be in the release 2.2.1

نصائح أخرى

You have to register DAL.Entities.Tag and DTO.Objects.TagDto though you have same property names on Tag and TagDto

I guess some of the properties in the Tag class you are not mapping. If so use Ignore

Mapper.CreateMap<Tag, TagDto>().ForMember(x => x.value, opt => opt.Ignore());

Have a look at Here & Here & Here

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top