2017-09-25 138 views
0

我有以下的DB(基礎設施)類:Automapper配置2類一個

[Table("ApplicationDriverEquipments")] 
public partial class ApplicationDriverEquipment 
{ 
    public int Id { get; set; } 
    [StringLength(256)] 
    public string Make { get; set; } 
    [StringLength(256)] 
    public string Model { get; set; } 
    [StringLength(256)] 
    public string Year { get; set; } 
    [StringLength(256)] 
    public string VINNumber { get; set; } 
    [StringLength(256)] 
    public string PlateNumber { get; set; } 
    [StringLength(256)] 
    public string CurrentMileage { get; set; } 
    [StringLength(256)] 
    public string Length { get; set; } 


    public int TypeId { get; set; } 
    public virtual ApplicationDriverEquipmentType Type { get; set; } 

    public int DriverId { get; set; } 
    public virtual ApplicationDriver Driver { get; set; } 
} 

[Table("ApplicationDriverEquipmentTypes")] 
public partial class ApplicationDriverEquipmentType 
{ 
    public ApplicationDriverEquipmentType() 
    { 
     Equipments = new HashSet<ApplicationDriverEquipment>(); 
    } 

    public int Id { get; set; } 
    [Required] 
    [StringLength(256)] 
    public string Name { get; set; } 
    public virtual ICollection<ApplicationDriverEquipment> Equipments { get; set; } 
} 

及以下DTO(域)類:

public abstract class ApplicationDriverEquipmentAbstractDomain 
{ 
    public int Id { get; set; } 
    public string Make { get; set; } 
    public string Model { get; set; } 
    public string Year { get; set; } 
    public string PlateNumber { get; set; } 
    public string CurrentMileage { get; set; } 
    public string Type { get; protected set; } 
} 

public class ApplicationDriverEquipmentTractorDomain : ApplicationDriverEquipmentAbstractDomain 
{ 
    public ApplicationDriverEquipmentTractorDomain() 
    { 
     Type = ApplicationDriverEquipmentTypeStaticStringsDomain.Tractor; 
    } 
    public string VINNumber { get; set; } 
} 

public class ApplicationDriverEquipmentTrailerDomain : ApplicationDriverEquipmentAbstractDomain 
{ 
    public ApplicationDriverEquipmentTrailerDomain() 
    { 
     Type = ApplicationDriverEquipmentTypeStaticStringsDomain.Trailer; 
    } 

    public string Length { get; set; } 
} 

public class ApplicationDriverEquipmentStraightTruckDomain : ApplicationDriverEquipmentAbstractDomain 
{ 
    public ApplicationDriverEquipmentStraightTruckDomain() 
    { 
     Type = ApplicationDriverEquipmentTypeStaticStringsDomain.StraightTruck; 
    } 

    public string VINNumber { get; set; } 
    public string Length { get; set; } 
} 

public class ApplicationDriverEquipmentCargoVanDomain : ApplicationDriverEquipmentAbstractDomain 
{ 
    public ApplicationDriverEquipmentCargoVanDomain() 
    { 
     Type = ApplicationDriverEquipmentTypeStaticStringsDomain.CargoVan; 
    } 

    public string VINNumber { get; set; } 
    public string Length { get; set; } 
} 

public static class ApplicationDriverEquipmentTypeStaticStringsDomain 
{ 
    public const string Tractor = "Tractor"; 
    public const string Trailer = "Trailer"; 
    public const string StraightTruck = "Straight Truck"; 
    public const string CargoVan = "Cargo Van"; 
} 

我寫了下面Automapper規則來解決它:

 CreateMap<Domain.POCO.Application.ApplicationDriverEquipmentTractorDomain, Infrastructure.Asset.ApplicationDriverEquipment>() 
      .ForMember(c => c.Type.Name, p => p.UseValue<string>(Domain.StaticStrings.ApplicationDriverEquipmentTypeStaticStringsDomain.Tractor)); 
     CreateMap<Domain.POCO.Application.ApplicationDriverEquipmentTrailerDomain, Infrastructure.Asset.ApplicationDriverEquipment>() 
      .ForMember(c => c.Type.Name, p => p.UseValue<string>(Domain.StaticStrings.ApplicationDriverEquipmentTypeStaticStringsDomain.Trailer)); 
     CreateMap<Domain.POCO.Application.ApplicationDriverEquipmentStraightTruckDomain, Infrastructure.Asset.ApplicationDriverEquipment>() 
      .ForMember(c => c.Type.Name, p => p.UseValue<string>(Domain.StaticStrings.ApplicationDriverEquipmentTypeStaticStringsDomain.StraightTruck)); 
     CreateMap<Domain.POCO.Application.ApplicationDriverEquipmentCargoVanDomain, Infrastructure.Asset.ApplicationDriverEquipment>() 
      .ForMember(c => c.Type.Name, p => p.UseValue<string>(Domain.StaticStrings.ApplicationDriverEquipmentTypeStaticStringsDomain.CargoVan)); 

我得到了一個錯誤:

Expression 'c => c.Type.Name' must resolve to top-level member and not any child object's properties. Use a custom resolver on the child type or the AfterMap option instead.

UPDATE

我重寫地圖:

 CreateMap<Domain.POCO.Application.ApplicationDriverEquipmentTractorDomain, Infrastructure.Asset.ApplicationDriverEquipment>() 
      .AfterMap((src, dest)=> dest.Type.Name = Domain.StaticStrings.ApplicationDriverEquipmentTypeStaticStringsDomain.Tractor); 
     CreateMap<Domain.POCO.Application.ApplicationDriverEquipmentTrailerDomain, Infrastructure.Asset.ApplicationDriverEquipment>() 
      .AfterMap((src, dest) => dest.Type.Name = Domain.StaticStrings.ApplicationDriverEquipmentTypeStaticStringsDomain.Trailer); 
     CreateMap<Domain.POCO.Application.ApplicationDriverEquipmentStraightTruckDomain, Infrastructure.Asset.ApplicationDriverEquipment>() 
      .AfterMap((src, dest) => dest.Type.Name = Domain.StaticStrings.ApplicationDriverEquipmentTypeStaticStringsDomain.StraightTruck); 
     CreateMap<Domain.POCO.Application.ApplicationDriverEquipmentCargoVanDomain, Infrastructure.Asset.ApplicationDriverEquipment>() 
      .AfterMap((src, dest) => dest.Type.Name = Domain.StaticStrings.ApplicationDriverEquipmentTypeStaticStringsDomain.CargoVan); 

,但現在我得到了一個錯誤:

Type Map configuration: ApplicationDriverEquipmentTractorDomain -> ApplicationDriverEquipment Domain.POCO.Application.ApplicationDriverEquipmentTractorDomain -> Infrastructure.Asset.ApplicationDriverEquipment

Property: Type ---> AutoMapper.AutoMapperMappingException: Missing type map configuration or unsupported mapping.

Mapping types:

String -> ApplicationDriverEquipmentType

System.String -> Infrastructure.Asset.ApplicationDriverEquipmentType

看來,我不知道如何正確地關聯

+0

類型是你的類中的字符串,它有一個名稱屬性? – ironstone13

+0

@ ironstone13,Type是ApplicationDriverEquipmentAbstractDomain類的字符串,但ApplicationDriverEquipment類型爲ApplicationDriverEquipmentType –

+0

嗨,@Oleh Sh,對於羅嗦和迭代響應抱歉,但我終於寫下了它,請參閱下面的答案。如果你有任何問題,讓我知道 – ironstone13

回答

1

你正試圖從
ApplicationDriverEquipmentTractorDomain.Type地圖是string

ApplicationDriverEquipment.TypeApplicationDriverEquipmentType

哪裏是你的映射配置是什麼?

是否有可能將字符串映射到ApplicationDriverEquipmentType
當然,你可以有string Name,但你從哪裏得到IdEquipments

我懷疑你不想每次映射時創建該類型的新實例,而是你需要從一些字典裏查一個實例,排序的registry pattern

爲了實現這個想法,你只需要

  1. 加載所有ApplicationDriverEquipmentType從DB
  2. 把它們放在一本字典(假設名字是唯一的)
  3. 註冊一個custom type convertercustom value resolver如下

一種方式來實現,這將是使用custom type converter
您可以使用類似
void ConvertUsing(Func<TSource, TDestination> mappingFunction);
並把自己的功能,將解決你的ApplicationDriverEquipmentType按名稱,假設名稱是唯一這樣的:

var applicationEquipments = new ApplicationDriverEquipmentTypeRepository().FindAll(); // get all the values somehow from db 
var dictionary = applicationEquipments.ToDictionary(x=>x.Name); 
Func<string, ApplicationDriverEquipmentType> resolver = x=>dictionary[x]; 

另一種方式來做到這將是使用custom value resolver
本質上,這個想法將是相同的 - 預加載對象的地圖,只有你「插入」的方式將是不同的

0

嘗試使用MapFrom方法代替:

.ForMember(c => c.Type.Name, p => p.MapFrom(s => Domain.StaticStrings.ApplicationDriverEquipmentTypeStaticStringsDomain.Tractor)); 
+0

@raimondBurgaj同樣的錯誤 –

+0

@OlegSh爲什麼你需要在映射邏輯中設置像這樣的'c => c.Type.Name'類型。據我所見,它是一個簡單的字符串屬性,所以它必須是'c => c.Type' –

+0

@raimondBurgaj,正如你所看到的,Type有類型ApplicationDriverEquipmentType,而不是目標類中的字符串:) –