2017-04-26 92 views
1

之間工作假設該枚舉合同:Automapper不類和結構AfterMap

[DataContract] 
public enum ReportType_DTO 
{ 
    [EnumMember] 
    Voice, 
    [EnumMember] 
    Text, 
    [EnumMember] 
    File 
} 

其具有從0三個成員至2中的另一側我有另一個枚舉具有7構件爲:

public enum RptType 
{ 
    Word = 0, 
    Dynamic = 1, 
    Basic = 2, 
    StructuredReport = 3, 
    Word2007 = 4, 
    PDF = 5, 
    WebReport = 6, 
    WebTemplate = 7 
} 

所以我配置映射爲:

var mapper1 = new MapperConfiguration((cfg) => 
      cfg.CreateMap<Report_C, Report_DTO>().AfterMap((reportC, reportDTO) => 
      { 
       switch ((RptType)reportC.Type) 
       { 
        case RptType.Dynamic: 
        case RptType.PDF: 
        case RptType.Word: 
        case RptType.Word2007: 
        case RptType.WebTemplate: 
         reportDTO.Type = ReportType_DTO.File; 
         break; 
        case RptType.StructuredReport: 
         reportDTO.Type = ReportType_DTO.Voice; 
         break; 
        case RptType.Basic: 
        case RptType.WebReport: 
         reportDTO.Type = ReportType_DTO.Text; 
         break; 
       } 
       reportDTO.ReportUID = reportC.SOPInstanceUID; 
      })) 
      .CreateMapper(); 

,並通過一個映射集之一:

var foundReports = pacsReports.Collection.Select(r => mapper1.Map<Report_DTO>(r)).ToList(); 

情況下RptType.StructuredReport發生對集合成員之一,但是當我檢查了收集它似乎道具沒有得到新的價值,如下圖: enter image description here

這是明顯的在客戶端,我們結束了像異常:

枚舉值「3」是無效的類型「xxx.ReportType_DTO」和無法序列。如果類型具有DataContractAttribute屬性,請確保存在必要的枚舉值並使用EnumMemberAttribute屬性標記。

是否有另一種方法強制Automapper顯式更改值?

UPDATE1:

Report_DTO爲結構類型但是Report_C是一個類,它可以是原因(像呼叫通過引用或通過映射值struct調用)?

UPDATE2:

struct的原因是,通過改變結構來上課它工作得很好,但我回國DTO_OUT作爲結構出於某種原因,迫使操作不空回,所以我不能改變他們上課,我相信必須有一個解決方案告訴通過引用autommaper調用,我認爲AfterMape是一個無效的方法,改變輸入參數調用引用機制。

任何想法和幫助將不勝感激。

+0

呀,'struct'絕對可以成爲一個理由 - 要修改的副本。 –

+0

讓我改變它'class'將盡快回來。 – Aria

+0

@IvanStoev是的,這是我們猜測的問題,但我不能改變結構到類,因爲我在更新2中思考,你的意見是什麼? – Aria

回答

2

有沒有辦法讓AutoMapper通過struct參照AfterMap的操作。所以你需要一個不同的方法,而不是基於AfterMap

一種方法是創建從RptTypeReportType_DTO的映射,將開關邏輯封裝在ConvertUsing中。然後創建一個從Report_C映射到Report_DTO典型ForMember設置:

var mapper1 = new MapperConfiguration(cfg => 
{ 
    cfg.CreateMap<RptType, ReportType_DTO>().ConvertUsing(rptType => 
    { 
     switch (rptType) 
     { 
      case RptType.StructuredReport: 
       return ReportType_DTO.Voice; 
      case RptType.Basic: 
      case RptType.WebReport: 
       return ReportType_DTO.Text; 
      default: 
       return ReportType_DTO.File; 
     } 
    }); 

    cfg.CreateMap<Report_C, Report_DTO>() 
     .ForMember(reportDTO => reportDTO.Type, opt => opt.MapFrom(reportC => (RptType)reportC.Type)) 
     .ForMember(reportDTO => reportDTO.ReportUID, opt => opt.MapFrom(reportC => reportC.SOPInstanceUID)); 
}) 
.CreateMapper(); 
+0

投票贊成,是的,'ConvertUsing'可以成爲解決方案,但仍然存在一些問題,即所有成員都應該手動映射,Automapper無法自動執行。 – Aria

+0

那麼,它會爲具有相同名稱和類型的屬性「自動」。你只需要指定上面的差異(首先是因爲不同的類型,其他因爲不同的名稱)。 –