编写AutoMapper代码最有效的方法?

时间:2017-04-14 13:20:14

标签: c# automapper

我最近给了Automapper一个镜头,一旦我开始工作,它绝对太棒了。问题是我必须编写的用于设置Automapper的实际代码有点粗略,我想知道我这样做的方式是否可以改进或简化。我使用它(在下面的示例中)将我的实体转换为viewmodel。字段名称完全不同,因此我必须手动创建映射(AFAIK)

public static class AutoMapperConfig
{
    public static void RegisterMappings()
    {
        Mapper.Initialize(cfg =>
        {
            cfg.CreateMap<customer_master, CustomerViewModel>()
            .ForMember
                (dst => dst.FirstName, src => src.MapFrom(e => e.cm_firstname))
            .ForMember
                (dst => dst.LastName, src => src.MapFrom(e => e.cm_lastname))
            .ForMember
                (dst => dst.Id, src => src.MapFrom(e => e.cm_id))
            .ForMember
                (dst => dst.Address1, src => src.MapFrom(e => e.cm_address1))
            .ForMember
                (dst => dst.Address2, src => src.MapFrom(e => e.cm_address2))
            .ForMember
                (dst => dst.City, src => src.MapFrom(e => e.cm_city))
            .ForMember
                (dst => dst.State, src => src.MapFrom(e => e.cm_state))
            .ForMember
                (dst => dst.Zip, src => src.MapFrom(e => e.cm_zip))
            .ForMember
                (dst => dst.Country, src => src.MapFrom(e => e.cm_country))
            .ForMember
                (dst => dst.Email, src => src.MapFrom(e => e.cm_email))
            .ForMember
                (dst => dst.Phone, src => src.MapFrom(e => e.cm_phone))
            .ForMember
                (dst => dst.Fax, src => src.MapFrom(e => e.cm_fax))
            .ForMember
                (dst => dst.Active, src => src.MapFrom(e => e.cm_active))
            .ForMember
                (dst => dst.Company, src => src.MapFrom(e => e.cm_company));

            cfg.CreateMap<CustomerViewModel, customer_master>()
            .ForMember
                (dst => dst.cm_firstname, src => src.MapFrom(e => e.FirstName))
            .ForMember
                (dst => dst.cm_lastname, src => src.MapFrom(e => e.LastName))
            .ForMember
                (dst => dst.cm_id, src => src.MapFrom(e => e.Id))
            .ForMember
                (dst => dst.cm_address1, src => src.MapFrom(e => e.Address1))
            .ForMember
                (dst => dst.cm_address2, src => src.MapFrom(e => e.Address2))
            .ForMember
                (dst => dst.cm_city, src => src.MapFrom(e => e.City))
            .ForMember
                (dst => dst.cm_state, src => src.MapFrom(e => e.State))
            .ForMember
                (dst => dst.cm_zip, src => src.MapFrom(e => e.Zip))
            .ForMember
                (dst => dst.cm_country, src => src.MapFrom(e => e.Country))
            .ForMember
                (dst => dst.cm_email, src => src.MapFrom(e => e.Email))
            .ForMember
                (dst => dst.cm_phone, src => src.MapFrom(e => e.Phone))
            .ForMember
                (dst => dst.cm_fax, src => src.MapFrom(e => e.Fax))
            .ForMember
                (dst => dst.cm_active, src => src.MapFrom(e => e.Active))
            .ForMember
                (dst => dst.cm_company, src => src.MapFrom(e => e.Company));

        });
    }
}

然后在Global.asax

AutoMapperConfig.RegisterMappings();

我的问题主要是:

  1. 字段名称是否必须像这样明确地映射,因为名称是如此不同?
  2. 有没有办法只编写第一张地图,然后再将它用于第二张地图?实体 - &gt; ViewModel与ViewModel相同 - &gt;实体,这两次写这些似乎是多余的。我想我在这里寻找某种双向选项。

3 个答案:

答案 0 :(得分:2)

如果字段名称不同则必须使用,对于双向,您只能编写一个映射,最后添加:

.ReverseMap()

答案 1 :(得分:2)

您的所有转化似乎都遵循相同的模式:成员X映射到成员cm_X。如果是这种情况,您可以将代码简化为:

Mapper.Initialize(cfg => {      
     // will remove "cm_" from destination when matching          
     // the fact you have different casing (Address vs cm_address)
     // is fine and is already handled
     cfg.RecognizeDestinationPrefixes(new [] {"cm_"});
     // will remove "cm_" from source when mapping
     cfg.RecognizePrefixes(new[] { "cm_" });
     // will map in both directions
     cfg.CreateMap<Entity, Dto>().ReverseMap();                
});

答案 2 :(得分:1)

如果字段名称具有明确的模式,例如示例中的cm_,则可以查看定义约定。见https://github.com/AutoMapper/AutoMapper/wiki/Conventions。也许这将照顾其中的大部分?