Automapper AutoMapper.AutoMapperMappingException: Error mapping types

13,764

Your CityDto class has a collection of Countries

[MapsTo(typeof(City))] [MapsFrom(typeof(City))] 
public class CityDto : EntityDto<Int32> 
{ 
    public Int32 CountryID { get; set; }
    public virtual ICollection<CountryDto> Country { get; set; } 
    public string Name { get; set; } 
}

But your City class has a single Country.

public class City : BaseEntity<Int32>
{        
    public string Name { get; set; }
    public Int32 CountryID { get; set; }
    public virtual Country Country { get; set; }
}

How are you mapping them?

Share:
13,764

Related videos on Youtube

Martin Spasovski
Author by

Martin Spasovski

Updated on June 04, 2022

Comments

  • Martin Spasovski
    Martin Spasovski almost 2 years

    I am getting a peculiar error with Automapper

    Error messages:

    Mapping types:
    TransportOffer -> TransportOfferDto
    Model.TransportOffer -> Dto.TransportOfferDto
    
    Type Map configuration:
    TransportOffer -> TransportOfferDto
    Model.TransportOffer -> Dto.TransportOfferDto
    
    Property:
    FromCity ---> AutoMapper.AutoMapperMappingException: Error mapping types.
    
    Mapping types:
    City -> CityDto
    Model.City -> Dto.CityDto
    
    Type Map configuration:
    City -> CityDto
    Model.City -> Dto.CityDto
    
    Property:
    Country ---> System.TypeLoadException: Method 'Add' in type 'Proxy_System.Collections.Generic.ICollection`1[[Dto.CountryDto, BusinessLogic, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null]]__17474517' from assembly 'AutoMapper.Proxies, Version=0.0.0.0, Culture=neutral, PublicKeyToken=be96cd2c38ef1005' does not have an implementation.
    

    Below are my entities and DTO and the query that retrieves the data. I am using Automapper 7.0.1 and Automapper.Attributes 6.0.1

    I have tried also with custom mapping configuration and the error is the same.

    Here is the Automapper custom property configuration:

    Mapper.Initialize
    (
        config =>
        {
            config.CreateMap<TransportOfferDto, TransportOffer>()
                .ForMember(dest => dest.FromCity, conf => conf.MapFrom(src => src.FromCity))
                .ForMember(dest => dest.FromCountry, conf => conf.MapFrom(src => src.FromCountry))
                .ForMember(dest => dest.ToCity, conf => conf.MapFrom(src => src.ToCity))
                .ForMember(dest => dest.ToCountry, conf => conf.MapFrom(src => src.ToCountry));
             }
         );
    

    Country - entity:

    public class Country : BaseEntity<Int32>
    {        
        public string Name { get; set; }
        public string Code { get; set; }
        public string Capital { get; set; }
        public Int32 TotalSold { get; set; }
    }
    

    CountryDto

    [MapsTo(typeof(Country))]
    [MapsFrom(typeof(Country))]
    public class CountryDto : EntityDto<Int32>
    {
        public string Name { get; set; }
        public string Code { get; set; }
        public string Capital { get; set; }
        public Int32 TotalSold { get; set; }
    }
    

    City - entity:

    public class City : BaseEntity<Int32>
    {        
        public string Name { get; set; }
        public Int32 CountryID { get; set; }
        public virtual Country Country { get; set; }
    }
    

    CityDto

    [MapsTo(typeof(City))]
    [MapsFrom(typeof(City))]
    public class CityDto : EntityDto<Int32>
    {
        public Int32 CountryID { get; set; }
        public virtual ICollection<CountryDto> Country { get; set; }
    
        public string Name { get; set; }
    
    }
    

    TransportOffer - entity:

    public class TransportOffer : BaseEntity<Guid>
    {
        public Guid TransportToken { get; set; }
        public DateTime Date { get; set; }
        public Int32 FromCityID { get; set; }
        public  virtual City FromCity { get; set; }
        public Int32 FromCountryID { get; set; }
        public virtual Country FromCountry { get; set; }
        public Int32 ToCityID { get; set; }
        public virtual City ToCity { get; set; }
        public Int32 ToCountryID { get; set; }
        public virtual Country ToCountry { get; set; }
    }
    

    TransportOfferDto:

    [MapsTo(typeof(TransportOffer))]
    [MapsFrom(typeof(TransportOffer))]
    public class TransportOfferDto : EntityDto<Guid>
    {
        public Guid TransportToken { get; set; }
        public DateTime Date { get; set; }    
        public Int32 FromCityID { get; set; }
        public virtual CityDto FromCity { get; set; }       
        public Int32 FromCountryID { get; set; }
        public virtual CountryDto FromCountry { get; set; } 
        public Int32 ToCityID { get; set; }
        public virtual CityDto ToCity { get; set; }
        public Int32 ToCountryID { get; set; }
        public virtual Country ToCountry { get; set; }
    } 
    

    Query

    var query = Repository.GetAll()
                .Include(x => x.FromCountry)
                .Include(x => x.FromCity)
                .Include(x => x.ToCountry)
                .Include(x => x.ToCity)
                .Where(p => p.MembershipID == input).ToList();
    
    return ObjectMapper.Map<List<TransportOfferDto>>(query);
    
    • V0ldek
      V0ldek over 5 years
      You probably need to show us the remaining DTOs as well.
    • Mel Gerats
      Mel Gerats over 5 years
      Did you create a mapping for Country and City?
    • Lucian Bargaoanu
      Lucian Bargaoanu over 5 years
      I'm guessing you have somewhere a map for ICollection :)
    • Martin Spasovski
      Martin Spasovski over 5 years
      @V0ldek - that is the complete DTO it is a mapping table.
    • Martin Spasovski
      Martin Spasovski over 5 years
      @MelGerats - The mapping for country and city is made the same way as MapsFrom/MapsTo with automapper attributes
    • Martin Spasovski
      Martin Spasovski over 5 years
      @LucianBargaoanu - No I dont have mapping for ICollection
    • Mel Gerats
      Mel Gerats over 5 years
      public virtual ICollection<CountryDto> you do
    • Martin Spasovski
      Martin Spasovski over 5 years
      @MelGerats - Yes you're right, I forgot, Do i need to add specific ICollection mapping in the automapper configuration?
    • V0ldek
      V0ldek over 5 years
      You don't, Automapper is smart enough to map an ICollection<From> to an ICollection<To>. But it won't automatically map an object to a collection of objects, see Mel Gerats answer.
  • Martin Spasovski
    Martin Spasovski over 5 years
    I am not mapping them anyhow I think that the DTO it should be without the ICollection??!!
  • Mel Gerats
    Mel Gerats over 5 years
    I think so too!
  • Martin Spasovski
    Martin Spasovski over 5 years
    Got it working, the ICollection was the problem, it somehow got c/p from another class... Thank you all.
  • Lucian Bargaoanu
    Lucian Bargaoanu over 5 years
    And you actually have an ICollection map. That happens because CreateMissingTypeMaps is true. Setting it to false would make things easier to understand.