PageRenderTime 57ms CodeModel.GetById 19ms RepoModel.GetById 0ms app.codeStats 0ms

/src/FluentNHibernate/Utils/Reflection/ReflectionHelper.cs

http://github.com/jagregory/fluent-nhibernate
C# | 137 lines | 110 code | 27 blank | 0 comment | 23 complexity | f52008c6517c81ba8babb3f4584b87c8 MD5 | raw file
Possible License(s): BSD-3-Clause, CC-BY-SA-3.0, Apache-2.0
  1. using System;
  2. using System.Collections.Generic;
  3. using System.Linq.Expressions;
  4. using System.Reflection;
  5. using FluentNHibernate;
  6. using FluentNHibernate.Automapping;
  7. namespace FluentNHibernate.Utils.Reflection
  8. {
  9. public static class ReflectionHelper
  10. {
  11. public static Type AutomappingTypeForEntityType(Type entityType)
  12. {
  13. return typeof(AutoMapping<>).MakeGenericType(entityType);
  14. }
  15. public static Member GetMember<TModel, TReturn>(Expression<Func<TModel, TReturn>> expression)
  16. {
  17. return GetMember(expression.Body);
  18. }
  19. public static Member GetMember<TModel>(Expression<Func<TModel, object>> expression)
  20. {
  21. return GetMember(expression.Body);
  22. }
  23. public static Accessor GetAccessor<MODEL>(Expression<Func<MODEL, object>> expression)
  24. {
  25. MemberExpression memberExpression = GetMemberExpression(expression.Body);
  26. return getAccessor(memberExpression);
  27. }
  28. public static Accessor GetAccessor<MODEL, T>(Expression<Func<MODEL, T>> expression)
  29. {
  30. MemberExpression memberExpression = GetMemberExpression(expression.Body);
  31. return getAccessor(memberExpression);
  32. }
  33. private static bool IsIndexedPropertyAccess(Expression expression)
  34. {
  35. return IsMethodExpression(expression) && expression.ToString().Contains("get_Item");
  36. }
  37. private static bool IsMethodExpression(Expression expression)
  38. {
  39. return expression is MethodCallExpression || (expression is UnaryExpression && IsMethodExpression((expression as UnaryExpression).Operand));
  40. }
  41. private static Member GetMember(Expression expression)
  42. {
  43. if (IsIndexedPropertyAccess(expression))
  44. return GetDynamicComponentProperty(expression).ToMember();
  45. if (IsMethodExpression(expression))
  46. return ((MethodCallExpression)expression).Method.ToMember();
  47. var memberExpression = GetMemberExpression(expression);
  48. return memberExpression.Member.ToMember();
  49. }
  50. private static PropertyInfo GetDynamicComponentProperty(Expression expression)
  51. {
  52. Type desiredConversionType = null;
  53. MethodCallExpression methodCallExpression = null;
  54. var nextOperand = expression;
  55. while (nextOperand != null)
  56. {
  57. if (nextOperand.NodeType == ExpressionType.Call)
  58. {
  59. methodCallExpression = nextOperand as MethodCallExpression;
  60. desiredConversionType = desiredConversionType ?? methodCallExpression.Method.ReturnType;
  61. break;
  62. }
  63. if (nextOperand.NodeType != ExpressionType.Convert)
  64. throw new ArgumentException("Expression not supported", "expression");
  65. var unaryExpression = (UnaryExpression)nextOperand;
  66. desiredConversionType = unaryExpression.Type;
  67. nextOperand = unaryExpression.Operand;
  68. }
  69. var constExpression = methodCallExpression.Arguments[0] as ConstantExpression;
  70. return new DummyPropertyInfo((string)constExpression.Value, desiredConversionType);
  71. }
  72. private static MemberExpression GetMemberExpression(Expression expression)
  73. {
  74. return GetMemberExpression(expression, true);
  75. }
  76. private static MemberExpression GetMemberExpression(Expression expression, bool enforceCheck)
  77. {
  78. MemberExpression memberExpression = null;
  79. if (expression.NodeType == ExpressionType.Convert)
  80. {
  81. var body = (UnaryExpression) expression;
  82. memberExpression = body.Operand as MemberExpression;
  83. }
  84. else if (expression.NodeType == ExpressionType.MemberAccess)
  85. {
  86. memberExpression = expression as MemberExpression;
  87. }
  88. if (enforceCheck && memberExpression == null)
  89. {
  90. throw new ArgumentException("Not a member access", "expression");
  91. }
  92. return memberExpression;
  93. }
  94. private static Accessor getAccessor(MemberExpression memberExpression)
  95. {
  96. var list = new List<Member>();
  97. while (memberExpression != null)
  98. {
  99. list.Add(memberExpression.Member.ToMember());
  100. memberExpression = memberExpression.Expression as MemberExpression;
  101. }
  102. if (list.Count == 1)
  103. {
  104. return new SingleMember(list[0]);
  105. }
  106. list.Reverse();
  107. return new PropertyChain(list.ToArray());
  108. }
  109. }
  110. }