Automapper将少量源对象属性映射到目标对象,并将少数源映射到其复杂的子对象属性

时间:2018-01-09 16:50:39

标签: c# automapper

public class Restaurant 
{
        public int RestaurantId { get; set; }
        public string Name { get; set; }
        public string Description { get; set; }
        public string Slug { get; set; }
        public bool Active { get; set; }
        public string Address1 { get; set; }
        public string Address2 { get; set; }
        public string ZipCode { get; set; }
        public string City { get; set; }
        public decimal? Lat { get; set; }
        public decimal? Long { get; set; }
}

public class RestaurantInfo 
{
        public int RestaurantId { get; set; }
        public string Name { get; set; }
        public string Description { get; set; }
        public string Slug { get; set; }
        public bool Active { get; set; }
        public Address Address { get; set; }
}

public class Address
{
        public string Address1 { get; set; }
        public string Address2 { get; set; }
        public string ZipCode { get; set; }
        public string City { get; set; }
        public decimal? Lat { get; set; }
        public decimal? Long { get; set; }
}

自动映射器

public class AutoMapperProfile : Profile
    {
        public AutoMapperProfile()
        {
            CreateMap<Restaurant, RestaurantInfo>();

            CreateMap<Restaurant, Address>();
        }
    }

public RestaurantInfo GetRestaurantById(IMapper mapper)
    {

        var restaurant = new Restaurant
            {   
                RestaurantId = 1,
                Name = "Blueline",
                Slug =  "Blueline",
                Active = true,
                Address1 = "XYZ",
                Address2 = "PQR"
            };

        return mapper.Map<Restaurant>(restaurantInfo);    
    }

我的源类是Restaurant,Destination类是RestaurantInfo。自动映射器正在将餐厅转换回RestaurantInfo,但问题是RestaurantInfo的Address属性未初始化,并且所有与地址相关的属性都属于Restaurant。我认为我的映射代码不正确。建议我正确映射上述问题。

2 个答案:

答案 0 :(得分:1)

您可以使用ForPath方法

对其进行归档
// Configure AutoMapper
Mapper.Initialize(
    cfg => cfg.CreateMap<Restaurant, RestaurantInfo>()
    .ForPath(dest => dest.Address.Address1, opt => opt.MapFrom(src => src.Address1))
    .ForPath(dest => dest.Address.Address2, opt => opt.MapFrom(src => src.Address2))
);

// Perform mapping
var restaurantInfo = Mapper.Map<Restaurant, RestaurantInfo>(restaurant);

另请参考Automapper documentation

答案 1 :(得分:0)

Automapper将按惯例展平对象 - https://stackoverflow.com/a/8259466/5121114。这意味着如果您从RestaurantInfo到Restaurant的映射,您可以使用“Address”为与Address对象相关的属性添加前缀,并且automapper会为您找出映射。但是,您要做的是取消对象并构造一个Address对象,这不是一个开箱即用的功能。您可以编写扩展方法来实现此目的,如以下帖子中所述:http://martinburrows.net/blog/2016/01/18/automatic-unflattening-with-automapper

但是我更愿意明确我的映射:

CreateMap<Restaurant, RestaurantInfo>().ForMember(info => info.Address, 
                expression => expression.MapFrom(restaurant => new Address
                {
                    Address1 = restaurant.AddressAddress1,
                    Address2 = restaurant.AddressAddress2,
                    City = restaurant.AddressCity,
                    Lat = restaurant.AddressLat,
                    Long = restaurant.AddressLong,
                    ZipCode = restaurant.AddressZipCode
                }));