2015-11-06 77 views
0

我有聯盟和automapper投影的問題。Automapper投影和聯合

我有兩個實體:

public class Entity 
{ 
    public DateTime ActionDate { get; set; } 
    public int SomeProp { get; set; } 
} 

public class ExtendedEntity 
{ 
    public DateTime ActionDate { get; set; } 
    public int SomeProp { get; set; } 
    public int SomeOtherProp { get; set; } 
} 

和投影:

public class EntityProjection 
{ 
    public DateTime ActionDate { get; set; } 
    public int SomeProp { get; set; } 
    public int SomeOtherProp { get; set; } 
    public string Source { get; set; } 
} 

我的實體映射到一個投影,實體沒有SomeOtherProp,所以我設置0到它:

public class EntityProfile : Profile 
{ 
    protected override void Configure() 
    { 
     CreateMap<ExtendedEntity, EntityProjection>() 
      .ForMember(dest => dest.Source, opt => opt.MapFrom(src => "ext entity")); 

     CreateMap<Entity, EntityProjection>() 
      .ForMember(dest => dest.SomeOtherProp, opt => opt.MapFrom(src => 0)) 
      .ForMember(dest => dest.Source, opt => opt.MapFrom(src => "entity")); 
    } 
} 

當我嘗試使用下一個代碼我得到錯誤:

var entities = context.Set<Entity>() 
      .Project().To<EntityProjection>(); 
var extEntities = context.Set<ExtendedEntity>() 
      .Project().To<EntityProjection>(); 
var result = entities.Union(extEntities).OrderBy(p => p.ActionDate).ToList(); 

錯誤文本:類型'UserQuery + EntityProjection'出現在單個LINQ to Entities查詢中的兩個結構不兼容的初始化中。一個類型可以是...

這意味着投影中的屬性必須以相同的順序初始化,我如何通過automapper設置投影屬性的初始化順序?

回答

0

很晚回答,短版似乎是「你不行」。

我有完全相同的問題(Can I force Automapper to initialise properties in a certain order?),最終映射了LINQ select語句中的所有內容。

爲了方便,我把它在我的DTO(切下來的代碼)靜態方法:

 public static IQueryable<MyDto> QueryableFromTaskType1(
     IQueryable<TaskType1> query) 
    { 
     return query.Select(src => new MyDto() 
     { 
      TaskId = src.Id, 
      AssetTypeName = src.Asset.AssetType.Name, 
      AssetId = src.Asset.Id, 
      AssetCode = src.Asset.Code, 
      AssetName = src.Asset.Name, 
     }); 
    } 

     public static IQueryable<MyDto> QueryableFromTaskType2(
     IQueryable<TaskType2> query) 
    { 
     return query.Select(src => new MyDto() 
     { 
      TaskId = src.Id, 
      AssetTypeName = src.AssetTypeName, 
      AssetId = src.AssetId, 
      AssetCode = src.AssetCode, 
      AssetName = src.AssetName, 
     }); 
    } 

那麼你可以得到你的對象,作爲一個IQueryable,只需通過他們通過適當的靜態方法(它將選擇附加到DTO中 - 或者以其他方式已知的項目),然後使用Union或Concat生成IQueryable。

唯一的缺點是Automapper通常會處理遞歸自動映射,儘管我很確定它不會很好地映射到SQL,所以你可能不會損失太多。