简体   繁体   English

基于Automapper约定的映射进行收集

[英]Automapper convention based mapping for collection

I have a project where I am trying to map a dictionary to a ViewModel.NamedProperty. 我有一个项目,正在尝试将字典映射到ViewModel.NamedProperty。 I am trying to use an AutoMapper custom resolver to perform the mapping based on a convention. 我正在尝试使用AutoMapper自定义解析器执行基于约定的映射。 My convention is that if the named property exists for the source dictionary key then map a property from the dictionary's value. 我的约定是,如果源字典键存在指定的属性,则从字典的值映射一个属性。 Here are my example classes: 这是我的示例类:

class User
{
   string Name {get;set;}
   Dictionary<string, AccountProp> CustomProperties {get;set;}
}

class AccountProp
{
   string PropertyValue {get;set;}
   //Some other properties

}

class UserViewModel
{
   string Name {get;set;}
   DateTime LastLogin {get;set;}
   string City {get;set}
}

var user = new User()
{
   Name = "Bob"   
};

user.CustomProperties.Add("LastLogin", new AccountProp(){PropertyValue = DateTime.Now};
user.CustomProperties.Add("City", new AccountProp(){PropertyValue = "SomeWhere"};

I want to map the User CustomProperties dictionary to the flattened UserViewModel by convention for all properties and I do not want to specify each property individually for the mapping. 我想按惯例将所有属性的User CustomProperties字典映射到展平的UserViewModel,并且我不想为映射单独指定每个属性。

What is the best way to go about this? 最好的方法是什么? I was thinking Custom value resolver but it seems that I have to specify each member I want to map individually. 我当时在考虑自定义值解析器,但似乎必须指定要单独映射的每个成员。 If I wanted to do that I would just manually perform the mapping without AutoMapper. 如果要这样做,我将在没有AutoMapper的情况下手动执行映射。

Below is code that serve the purpose. 以下是达到目的的代码。 Not sure whether it is good or not. 不确定它是否好。

Mapper.CreateMap<User, UserViewModel>()
    .ForMember(dest => dest.Name, opt => opt.MapFrom(src => src.Name))                // Optional
    .ForMember(dest => dest.City, opt => opt.MapFrom(src => src.CustomProperties.FirstOrDefault(x => x.Key == "City").Value.PropertyValue.ToString()))  // Handle null
    .ForMember(dest => dest.LastLogin, opt => opt.MapFrom(src => Convert.ToDateTime(src.CustomProperties.FirstOrDefault(x => x.Key == "LastLogin").Value.PropertyValue)));  //Handle null

I ended up creating a custom type converter to deal with this scenario and it works great: 我最终创建了一个自定义类型转换器来处理这种情况,并且效果很好:

public class ObjectToPropertyTypeConverter<TFromEntity> : ITypeConverter<TFromEntity, HashSet<Property>>
{
 //perform custom conversion here
}

I then implemented the Custom mapping as follows: 然后,我实现了自定义映射,如下所示:

 AutoMapper.Mapper.CreateMap<MyViewModel, HashSet<Property>>()
               .ConvertUsing<ObjectToPropertyTypeConverter<MyViewModel>>();

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM