AutoMapper 創建嵌套對象映射(原創)


之前在做DTO轉換時,用到AutoMapper。但DTO的層次太深了,無奈官方沒針對嵌套類型提供好的解決方案,於是自己實現了一下:

思路:采用遞歸和反射很好的避免手工創建嵌套對象的映射。

 

第一個版本,已經提交到:https://github.com/AutoMapper/AutoMapper/wiki/Nested-mappings

 1         /// <summary>
 2         /// 遞歸創建類型間的映射關系 (Recursively create mappings between types)
 3         ///created by cqwang
 4         /// </summary>
 5         /// <param name="sourceType"></param>
 6         /// <param name="destinationType"></param>
 7         public static void CreateNestedMappers(Type sourceType, Type destinationType)
 8         {
 9             PropertyInfo[] sourceProperties = sourceType.GetProperties(BindingFlags.Public | BindingFlags.Instance);
10             PropertyInfo[] destinationProperties = destinationType.GetProperties(BindingFlags.Public | BindingFlags.Instance);
11             foreach (var destinationProperty in destinationProperties)
12             {
13                 Type destinationPropertyType = destinationProperty.PropertyType;
14                 if (Filter(destinationPropertyType))
15                     continue;
16 
17                 PropertyInfo sourceProperty = sourceProperties.FirstOrDefault(prop => NameMatches(prop.Name, destinationProperty.Name));
18                 if (sourceProperty == null)
19                     continue;
20 
21                 Type sourcePropertyType=sourceProperty.PropertyType;
22                 if (destinationPropertyType.IsGenericType)
23                 {
24                     Type destinationGenericType = destinationPropertyType.GetGenericArguments()[0];
25                     if (Filter(destinationGenericType))
26                         continue;
27 
28                     Type sourceGenericType = sourcePropertyType.GetGenericArguments()[0];
29                     CreateMappers(sourceGenericType, destinationGenericType);
30                 }
31                 else
32                 {
33                     CreateMappers(sourcePropertyType, destinationPropertyType);
34                 }
35             }
36 
37             Mapper.CreateMap(sourceType, destinationType);
38         }
39 
40         /// <summary>
41         /// 過濾 (Filter)
42         /// </summary>
43         /// <param name="type"></param>
44         /// <returns></returns>
45         static bool Filter(Type type)
46         {
47             return type.IsPrimitive || NoPrimitiveTypes.Contains(type.Name);
48         }
49 
50         static readonly HashSet<string> NoPrimitiveTypes = new HashSet<string>() { "String", "DateTime", "Decimal" };
51 
52         private static bool NameMatches(string memberName, string nameToMatch)
53         {
54             return String.Compare(memberName, nameToMatch, StringComparison.OrdinalIgnoreCase) == 0;
55         }
View Code

 

后來自測中發現,要過濾的一些結構體可能很多,比較麻煩,所以自己又完善了下,有了第二個版本

第二個版本在公司內的一些服務中已經使用並上線,挺好。因為並未涉及到公司內的任何業務信息,只是簡單的思路和實現,所以這里貼出來給大家分享一下。

所有代碼為原創,轉載請注明出處。

 

其實,本沒有路,走過去,便是路。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM