ExpressionTool.cs 39 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950
  1. using System;
  2. using System.Collections.Generic;
  3. using System.Collections.ObjectModel;
  4. using System.Globalization;
  5. using System.Linq;
  6. using System.Linq.Expressions;
  7. using System.Reflection;
  8. using System.Text;
  9. namespace SqlSugar
  10. {
  11. public class ExpressionTool
  12. {
  13. internal static Expression GetConditionalExpression(Expression item)
  14. {
  15. ConstantExpression trueConstant = Expression.Constant(true, typeof(bool));
  16. ConstantExpression falseConstant = Expression.Constant(false, typeof(bool));
  17. // 创建条件表达式:item ? true : false
  18. Expression conditionalExpression = Expression.Condition(
  19. test: item,
  20. ifTrue: trueConstant,
  21. ifFalse: falseConstant
  22. );
  23. return conditionalExpression;
  24. }
  25. internal static bool IsNavMember(ExpressionContext context, Expression member)
  26. {
  27. var isNav = false;
  28. if (member is MemberExpression && (member as MemberExpression)?.Type?.IsClass()==true)
  29. {
  30. var memberExp = (member as MemberExpression);
  31. var name = memberExp?.Member?.Name;
  32. var type = memberExp?.Type;
  33. if (name!=null&&type!=null&&memberExp.Expression is ParameterExpression)
  34. {
  35. var rootExp = (memberExp.Expression as ParameterExpression);
  36. var entityInfo = context?.SugarContext?.Context?.EntityMaintenance?.GetEntityInfo(rootExp.Type);
  37. var navColumn = entityInfo.Columns.FirstOrDefault(it => it.PropertyName == name);
  38. isNav = navColumn?.Navigat != null;
  39. }
  40. }
  41. return isNav;
  42. }
  43. internal static bool IsSqlParameterDbType(ExpressionContext context, Expression member)
  44. {
  45. var isNav = false;
  46. if (context?.SugarContext!=null&&member is MemberExpression && (member as MemberExpression)?.Expression is ParameterExpression expression)
  47. {
  48. if (expression != null)
  49. {
  50. var typeEntity = context?.SugarContext.Context.EntityMaintenance.GetEntityInfo(expression.Type);
  51. var columnInfo = typeEntity.Columns.FirstOrDefault(it => it.PropertyName == ExpressionTool.GetMemberName(member));
  52. if (columnInfo?.SqlParameterDbType is Type)
  53. {
  54. return true;
  55. }
  56. if (columnInfo?.SqlParameterDbType is System.Data.DbType)
  57. {
  58. return true;
  59. }
  60. }
  61. }
  62. return isNav;
  63. }
  64. internal static SugarParameter GetParameterBySqlParameterDbType(int index,object value,ExpressionContext context, Expression member)
  65. {
  66. var expression=(member as MemberExpression)?.Expression;
  67. var typeEntity = context?.SugarContext.Context.EntityMaintenance.GetEntityInfo(expression.Type);
  68. var columnInfo = typeEntity.Columns.FirstOrDefault(it => it.PropertyName == ExpressionTool.GetMemberName(member));
  69. var columnDbType = columnInfo.SqlParameterDbType as Type;
  70. if (columnDbType != null)
  71. {
  72. var ParameterConverter = columnDbType.GetMethod("ParameterConverter").MakeGenericMethod(columnInfo.PropertyInfo.PropertyType);
  73. var obj = Activator.CreateInstance(columnDbType);
  74. var p = ParameterConverter.Invoke(obj, new object[] { value, index }) as SugarParameter;
  75. return p;
  76. }
  77. else
  78. {
  79. var paramter = new SugarParameter("@Common" + index, value)
  80. {
  81. DbType = (System.Data.DbType)columnInfo.SqlParameterDbType
  82. };
  83. if (columnInfo.SqlParameterSize!=null&& columnInfo.SqlParameterSize.ObjToInt()>0)
  84. {
  85. paramter.Size= columnInfo.SqlParameterSize.ObjToInt();
  86. }
  87. return paramter;
  88. }
  89. }
  90. public static List<string> ExtractMemberNames(Expression expression)
  91. {
  92. var memberNames = new List<string>();
  93. var currentExpression = (expression as LambdaExpression).Body;
  94. while (currentExpression != null && currentExpression.NodeType == ExpressionType.MemberAccess)
  95. {
  96. var memberExpression = (MemberExpression)currentExpression;
  97. memberNames.Add(memberExpression.Member.Name);
  98. currentExpression = memberExpression.Expression;
  99. }
  100. memberNames.Reverse(); // Reverse the list to get the correct order of member names
  101. return memberNames;
  102. }
  103. public static Expression<Func<T, bool>> ChangeLambdaExpression<T>(Expression<Func<T,bool>> exp,string replaceParameterName, string newParameterName)
  104. {
  105. var parameter = Expression.Parameter(typeof(T), newParameterName);
  106. // 替换Lambda表达式中指定参数名
  107. var visitor = new ParameterReplacer(replaceParameterName, parameter);
  108. var newBody = visitor.Visit(exp);
  109. return (Expression<Func<T, bool>>)newBody;
  110. }
  111. public static Expression ChangeLambdaExpression(Expression exp, Type targetType, string replaceParameterName, string newParameterName)
  112. {
  113. var parameter = Expression.Parameter(targetType, newParameterName);
  114. // 替换Lambda表达式中指定参数名
  115. var visitor = new ParameterReplacer(replaceParameterName, parameter);
  116. var newBody = visitor.Visit(exp);
  117. return newBody;
  118. }
  119. public static List<string> GetNewArrayMembers(NewArrayExpression newArrayExpression)
  120. {
  121. List<string> strings = new List<string>();
  122. // 获取数组元素的 MemberExpression,并输出属性名
  123. foreach (var expression in newArrayExpression.Expressions)
  124. {
  125. var memberExpression = expression as MemberExpression;
  126. if (memberExpression != null)
  127. {
  128. strings.Add(memberExpression.Member.Name);
  129. }
  130. else if (expression is ConstantExpression)
  131. {
  132. strings.Add((expression as ConstantExpression).Value+"");
  133. }
  134. }
  135. return strings;
  136. }
  137. public static List<string> GetTopLevelMethodCalls(Expression expression)
  138. {
  139. var methodCalls = new List<string>();
  140. GetTopLevelMethodCalls(expression, methodCalls);
  141. return methodCalls;
  142. }
  143. public static void GetTopLevelMethodCalls(Expression expression, List<string> methodCalls)
  144. {
  145. if (expression is MethodCallExpression methodCallExpression)
  146. {
  147. methodCalls.Add(methodCallExpression.Method.Name);
  148. if (methodCallExpression.Object is MethodCallExpression parentMethodCallExpression)
  149. {
  150. GetTopLevelMethodCalls(parentMethodCallExpression, methodCalls);
  151. }
  152. }
  153. else if (expression is LambdaExpression lambdaExpression)
  154. {
  155. GetTopLevelMethodCalls(lambdaExpression.Body, methodCalls);
  156. }
  157. }
  158. public static Dictionary<string, Expression> GetNewExpressionItemList(Expression lamExp)
  159. {
  160. var caseExp = GetLambdaExpressionBody(lamExp);
  161. if (caseExp is MemberInitExpression)
  162. {
  163. return GetMemberBindingItemList((caseExp as MemberInitExpression).Bindings);
  164. }
  165. var exp= caseExp as NewExpression;
  166. if (exp == null)
  167. {
  168. Check.ExceptionEasy("Use Select(it=>new class(){})", "导航查询请使用Select(it=>new class(){})");
  169. }
  170. var dict = new Dictionary<string, Expression>();
  171. for (int i = 0; i < exp.Arguments.Count; i++)
  172. {
  173. var arg = exp.Arguments[i];
  174. var parameterInfo = exp.Constructor.GetParameters()[i];
  175. dict.Add(parameterInfo.Name, arg);
  176. }
  177. return dict;
  178. }
  179. public static Dictionary<string, Expression> GetMemberBindingItemList(ReadOnlyCollection<MemberBinding> exp)
  180. {
  181. Dictionary<string, Expression> dict = new Dictionary<string, Expression>();
  182. // 获取MemberInitExpression中的每一个MemberBinding
  183. foreach (var binding in exp)
  184. {
  185. // 判断是MemberAssignment还是MemberListBinding
  186. if (binding is MemberAssignment assignment)
  187. {
  188. // 获取属性名和属性值
  189. string propertyName = assignment.Member.Name;
  190. dict.Add(assignment.Member.Name, assignment.Expression);
  191. }
  192. }
  193. return dict;
  194. }
  195. public static bool ContainsMethodName(BinaryExpression expression, string name)
  196. {
  197. var visitor = new MethodCallExpressionVisitor(name);
  198. var hasMethodCallWithName = visitor.HasMethodCallWithName(expression);
  199. return hasMethodCallWithName;
  200. }
  201. public static bool IsVariable(Expression expr)
  202. {
  203. var ps = new ParameterExpressionVisitor();
  204. ps.Visit(expr);
  205. return ps.Parameters.Count==0;
  206. }
  207. public static List<ParameterExpression> GetParameters(Expression expr)
  208. {
  209. var ps = new ParameterExpressionVisitor();
  210. ps.Visit(expr);
  211. return ps.Parameters;
  212. }
  213. public static bool IsComparisonOperatorBool(BinaryExpression binaryExp)
  214. {
  215. return binaryExp.NodeType.IsIn(ExpressionType.Equal,
  216. ExpressionType.GreaterThan, ExpressionType.GreaterThanOrEqual,
  217. ExpressionType.LessThan, ExpressionType.LessThanOrEqual);
  218. }
  219. public static string GetOperator(ExpressionType expressiontype)
  220. {
  221. switch (expressiontype)
  222. {
  223. case ExpressionType.And:
  224. return "&";
  225. case ExpressionType.AndAlso:
  226. return "AND";
  227. case ExpressionType.Equal:
  228. return "=";
  229. case ExpressionType.GreaterThan:
  230. return ">";
  231. case ExpressionType.GreaterThanOrEqual:
  232. return ">=";
  233. case ExpressionType.LessThan:
  234. return "<";
  235. case ExpressionType.LessThanOrEqual:
  236. return "<=";
  237. case ExpressionType.NotEqual:
  238. return "<>";
  239. case ExpressionType.Or:
  240. return "|";
  241. case ExpressionType.OrElse:
  242. return "OR";
  243. case ExpressionType.Add:
  244. case ExpressionType.AddChecked:
  245. return "+";
  246. case ExpressionType.Subtract:
  247. case ExpressionType.SubtractChecked:
  248. return "-";
  249. case ExpressionType.Divide:
  250. return "/";
  251. case ExpressionType.Multiply:
  252. case ExpressionType.MultiplyChecked:
  253. return "*";
  254. case ExpressionType.Modulo:
  255. return "%";
  256. case ExpressionType.Coalesce:
  257. throw new Exception("Expression no support ?? ,Use SqlFunc.IsNull");
  258. default:
  259. Check.ThrowNotSupportedException(string.Format(ErrorMessage.OperatorError, expressiontype.ToString()));
  260. return null;
  261. }
  262. }
  263. public static void GetOneToOneInfo<T>(SqlSugarProvider context,Expression<Func<T, object>> LeftObject, out MemberExpression memberExpression, out string navObjectName, out EntityColumnInfo navColumn, out EntityInfo navEntityInfo, out EntityColumnInfo navPkColumn)
  264. {
  265. memberExpression = ((LeftObject as LambdaExpression).Body as MemberExpression);
  266. var listItemType = typeof(T);
  267. var listItemEntity = context.EntityMaintenance.GetEntityInfo(listItemType);
  268. var listPkColumn = listItemEntity.Columns.Where(it => it.IsPrimarykey).FirstOrDefault();
  269. navObjectName = memberExpression.Member.Name;
  270. var navObjectName2 = navObjectName;
  271. var navObjectNamePropety = listItemType.GetProperty(navObjectName);
  272. var navObjectNameColumnInfo = listItemEntity.Columns.First(it => it.PropertyName == navObjectName2);
  273. Check.ExceptionEasy(navObjectNameColumnInfo.Navigat == null, $"{navObjectName} not [Navigat(..)] ", $"{navObjectName} 没有导航特性 [Navigat(..)] ");
  274. Check.ExceptionEasy(navObjectNameColumnInfo.Navigat.NavigatType != NavigateType.OneToOne, $"IncludeLeftJoin can only be one-on-one ", $"IncludeLeftJoin 只能是一对一 ");
  275. navColumn = listItemEntity.Columns.FirstOrDefault(it => it.PropertyName == navObjectNameColumnInfo.Navigat.Name);
  276. Check.ExceptionEasy(navColumn == null, "OneToOne navigation configuration error", $"OneToOne导航配置错误: 实体{ listItemEntity.EntityName } 不存在{navObjectNameColumnInfo.Navigat.Name}");
  277. var navType = navObjectNamePropety.PropertyType;
  278. navEntityInfo = context.EntityMaintenance.GetEntityInfo(navType);
  279. context.InitMappingInfo(navEntityInfo.Type);
  280. navPkColumn = navEntityInfo.Columns.Where(it => it.IsPrimarykey).FirstOrDefault();
  281. Check.ExceptionEasy(navPkColumn == null && navObjectNameColumnInfo.Navigat.Name2 == null, navEntityInfo.EntityName + "need primarykey", navEntityInfo.EntityName + " 需要主键");
  282. if (navObjectNameColumnInfo.Navigat.Name2.HasValue())
  283. {
  284. navPkColumn = navEntityInfo.Columns.Where(it => it.PropertyName == navObjectNameColumnInfo.Navigat.Name2).FirstOrDefault();
  285. }
  286. }
  287. public static List<ParameterExpression> ExpressionParameters(Expression expression)
  288. {
  289. List<ParameterExpression> parameters = null;
  290. if (expression is LambdaExpression)
  291. {
  292. if ((expression as LambdaExpression).Parameters != null)
  293. {
  294. parameters = (expression as LambdaExpression).Parameters.ToList();
  295. }
  296. }
  297. return parameters;
  298. }
  299. public static object GetValue(object value,ExpressionContext context)
  300. {
  301. if (value == null) return value;
  302. var type = value.GetType();
  303. if (type.IsEnum() && type != typeof(DateType) && type != typeof(JoinType) && type != typeof(OrderByType))
  304. {
  305. if (context.TableEnumIsString == true)
  306. {
  307. return value.ToString();
  308. }
  309. else
  310. {
  311. return Convert.ToInt64(value);
  312. }
  313. }
  314. else
  315. return value;
  316. }
  317. public static Expression GetLambdaExpressionBody(Expression expression)
  318. {
  319. Expression newExp = expression;
  320. if (newExp is LambdaExpression)
  321. {
  322. newExp = (newExp as LambdaExpression).Body;
  323. }
  324. return newExp;
  325. }
  326. public static string GetFirstTypeNameFromExpression(Expression expression)
  327. {
  328. if (expression is LambdaExpression lambda)
  329. {
  330. return GetFirstTypeNameFromExpression(lambda.Body);
  331. }
  332. else if (expression is MemberExpression member)
  333. {
  334. return member.Member.Name;
  335. }
  336. else if (expression is NewExpression newExpr)
  337. {
  338. return newExpr.Type.Name;
  339. }
  340. else if (expression is MethodCallExpression methodCall)
  341. {
  342. return GetFirstTypeNameFromExpression(methodCall.Arguments.FirstOrDefault());
  343. }
  344. return "";
  345. }
  346. public static string GetMethodName(Expression expression)
  347. {
  348. if (expression is MethodCallExpression)
  349. {
  350. return (expression as MethodCallExpression).Method.Name;
  351. }
  352. return null;
  353. }
  354. public static Type GetMemberInfoType(MemberInfo member)
  355. {
  356. switch (member.MemberType)
  357. {
  358. case MemberTypes.Event:
  359. return ((EventInfo)member).EventHandlerType;
  360. case MemberTypes.Field:
  361. return ((FieldInfo)member).FieldType;
  362. case MemberTypes.Method:
  363. return ((MethodInfo)member).ReturnType;
  364. case MemberTypes.Property:
  365. return ((PropertyInfo)member).PropertyType;
  366. default:
  367. return null;
  368. }
  369. }
  370. public static bool IsLogicOperator(string operatorValue)
  371. {
  372. return operatorValue == "&&" || operatorValue == "||" || operatorValue == "AND" || operatorValue == "OR";
  373. }
  374. public static bool IsLogicOperator(Expression expression)
  375. {
  376. return expression.NodeType == ExpressionType.And ||
  377. expression.NodeType == ExpressionType.AndAlso ||
  378. expression.NodeType == ExpressionType.Or ||
  379. expression.NodeType == ExpressionType.OrElse;
  380. }
  381. public static bool IsComparisonOperator(Expression expression)
  382. {
  383. return expression.NodeType != ExpressionType.And &&
  384. expression.NodeType != ExpressionType.AndAlso &&
  385. expression.NodeType != ExpressionType.Or &&
  386. expression.NodeType != ExpressionType.OrElse;
  387. }
  388. public static bool IsEqualOrLtOrGt(Expression expression)
  389. {
  390. return expression.NodeType== ExpressionType.Equal||
  391. expression.NodeType == ExpressionType.GreaterThan||
  392. expression.NodeType == ExpressionType.LessThan||
  393. expression.NodeType == ExpressionType.LessThanOrEqual ||
  394. expression.NodeType == ExpressionType.GreaterThanOrEqual
  395. ;
  396. }
  397. public static object GetMemberValue(MemberInfo member, Expression expression)
  398. {
  399. var rootExpression = expression as MemberExpression;
  400. var memberInfos = new Stack<MemberInfo>();
  401. var fieldInfo = member as System.Reflection.FieldInfo;
  402. object reval = null;
  403. MemberExpression memberExpr = null;
  404. while (expression is MemberExpression)
  405. {
  406. memberExpr = expression as MemberExpression;
  407. memberInfos.Push(memberExpr.Member);
  408. if (memberExpr.Expression == null)
  409. {
  410. var isProperty = memberExpr.Member.MemberType == MemberTypes.Property;
  411. var isField = memberExpr.Member.MemberType == MemberTypes.Field;
  412. if (isProperty)
  413. {
  414. try
  415. {
  416. reval = GetPropertyValue(memberExpr);
  417. }
  418. catch
  419. {
  420. reval = null;
  421. }
  422. }
  423. else if (isField)
  424. {
  425. reval = GetFiledValue(memberExpr);
  426. }
  427. }
  428. if (memberExpr.Expression == null)
  429. {
  430. }
  431. expression = memberExpr.Expression;
  432. }
  433. // fetch the root object reference:
  434. var constExpr = expression as ConstantExpression;
  435. if (constExpr == null)
  436. {
  437. return DynamicInvoke(rootExpression);
  438. }
  439. object objReference = constExpr.Value;
  440. // "ascend" back whence we came from and resolve object references along the way:
  441. while (memberInfos.Count > 0) // or some other break condition
  442. {
  443. var mi = memberInfos.Pop();
  444. if (mi.MemberType == MemberTypes.Property)
  445. {
  446. if (objReference == null)
  447. {
  448. Check.ExceptionEasy($"Expression error {rootExpression?.ToString()} expression, An empty reference appears in the expression to check if the parameter is null ", $"表达式错误 {rootExpression?.ToString()} 表达式中出现了空引用 检查参数是否为null ");
  449. }
  450. var objProp = objReference.GetType().GetProperties().Where(it=>it.Name== mi.Name).FirstOrDefault();
  451. if (objProp == null)
  452. {
  453. objReference = DynamicInvoke(expression, rootExpression == null ? memberExpr : rootExpression);
  454. }
  455. else
  456. {
  457. objReference = objProp.GetValue(objReference, null);
  458. }
  459. }
  460. else if (mi.MemberType == MemberTypes.Field)
  461. {
  462. var objField = objReference.GetType().GetField(mi.Name);
  463. if (objField == null)
  464. {
  465. objReference = DynamicInvoke(expression, rootExpression == null ? memberExpr : rootExpression);
  466. }
  467. else
  468. {
  469. objReference = objField.GetValue(objReference);
  470. }
  471. }
  472. }
  473. reval = objReference;
  474. return reval;
  475. }
  476. internal static Expression RemoveConvert(Expression item)
  477. {
  478. for (int i = 0; i < 10; i++)
  479. {
  480. if ((item is UnaryExpression) && (item as UnaryExpression).NodeType == ExpressionType.Convert)
  481. {
  482. item = (item as UnaryExpression).Operand;
  483. }
  484. else
  485. {
  486. break;
  487. }
  488. }
  489. return item;
  490. }
  491. internal static Expression RemoveConvertThanOne(Expression item)
  492. {
  493. for (int i = 0; i < 10; i++)
  494. {
  495. if ((item is UnaryExpression)
  496. && (item as UnaryExpression).NodeType == ExpressionType.Convert
  497. && (item as UnaryExpression).Operand is UnaryExpression)
  498. {
  499. item = (item as UnaryExpression).Operand;
  500. }
  501. else
  502. {
  503. break;
  504. }
  505. }
  506. return item;
  507. }
  508. public static string GetMemberName(Expression expression)
  509. {
  510. if (expression is LambdaExpression)
  511. {
  512. expression = (expression as LambdaExpression).Body;
  513. }
  514. if (expression is UnaryExpression)
  515. {
  516. expression = ((UnaryExpression)expression).Operand;
  517. }
  518. var member = (expression as MemberExpression)?.Member?.Name;
  519. return member;
  520. }
  521. internal static object GetExpressionValue(Expression expression)
  522. {
  523. try
  524. {
  525. if (expression is ConstantExpression)
  526. {
  527. return (expression as ConstantExpression).Value;
  528. }
  529. else if (expression is MethodCallExpression)
  530. {
  531. return LambdaExpression.Lambda(expression).Compile().DynamicInvoke();
  532. }
  533. else
  534. {
  535. return GetMemberValue((expression as MemberExpression).Member, expression);
  536. }
  537. }
  538. catch
  539. {
  540. return LambdaExpression.Lambda(expression).Compile().DynamicInvoke();
  541. }
  542. }
  543. public static object GetFiledValue(MemberExpression memberExpr)
  544. {
  545. if (!(memberExpr.Member is FieldInfo))
  546. {
  547. return DynamicInvoke(memberExpr);
  548. }
  549. object reval = null;
  550. FieldInfo field = (FieldInfo)memberExpr.Member;
  551. Check.Exception(field.IsPrivate, string.Format(" Field \"{0}\" can't be private ", field.Name));
  552. reval = field.GetValue(memberExpr.Member);
  553. if (reval != null && reval.GetType().IsClass() && reval.GetType() != UtilConstants.StringType)
  554. {
  555. var fieldName = memberExpr.Member.Name;
  556. var proInfo = reval.GetType().GetProperty(fieldName);
  557. if (proInfo != null)
  558. {
  559. reval = proInfo.GetValue(reval, null);
  560. }
  561. var fieInfo = reval.GetType().GetField(fieldName);
  562. if (fieInfo != null)
  563. {
  564. reval = fieInfo.GetValue(reval);
  565. }
  566. if (fieInfo == null && proInfo == null)
  567. {
  568. Check.Exception(field.IsPrivate, string.Format(" Field \"{0}\" can't be private ", field.Name));
  569. }
  570. }
  571. return reval;
  572. }
  573. public static bool IsConstExpression(MemberExpression memberExpr)
  574. {
  575. var result = false;
  576. while (memberExpr != null && memberExpr.Expression != null)
  577. {
  578. var isConst = memberExpr.Expression is ConstantExpression;
  579. if (isConst)
  580. {
  581. result = true;
  582. break;
  583. }
  584. else if (memberExpr.Expression is BinaryExpression&&(memberExpr.Expression as BinaryExpression).NodeType==ExpressionType.ArrayIndex)
  585. {
  586. result = true;
  587. break;
  588. }
  589. memberExpr = memberExpr.Expression as MemberExpression;
  590. }
  591. return result;
  592. }
  593. public static object GetPropertyValue(MemberExpression memberExpr)
  594. {
  595. if (!(memberExpr.Member is PropertyInfo))
  596. {
  597. return DynamicInvoke(memberExpr);
  598. }
  599. object reval = null;
  600. PropertyInfo pro = (PropertyInfo)memberExpr.Member;
  601. reval = pro.GetValue(memberExpr.Member, null);
  602. if (reval != null && reval.GetType().IsClass() && reval.GetType() != UtilConstants.StringType)
  603. {
  604. var fieldName = memberExpr.Member.Name;
  605. var proInfo = reval.GetType().GetProperty(fieldName);
  606. if (proInfo != null)
  607. {
  608. reval = proInfo.GetValue(reval, null);
  609. }
  610. var fieInfo = reval.GetType().GetField(fieldName);
  611. if (fieInfo != null)
  612. {
  613. reval = fieInfo.GetValue(reval);
  614. }
  615. if (fieInfo == null && proInfo == null&& !reval.GetType().FullName.IsCollectionsList())
  616. {
  617. Check.Exception(true, string.Format(" Property \"{0}\" can't be private ", pro.Name));
  618. }
  619. }
  620. return reval;
  621. }
  622. public static object DynamicInvoke(Expression expression, MemberExpression memberExpression = null)
  623. {
  624. try
  625. {
  626. object value = Expression.Lambda(expression).Compile().DynamicInvoke();
  627. if (value != null && value.GetType().IsClass() && value.GetType() != UtilConstants.StringType && memberExpression != null)
  628. {
  629. value = Expression.Lambda(memberExpression).Compile().DynamicInvoke();
  630. }
  631. return value;
  632. }
  633. catch (InvalidOperationException ex)
  634. {
  635. return new MapperExpressionResolve(expression,ex).GetSql(); ;
  636. }
  637. catch (Exception ex)
  638. {
  639. throw new Exception("No support "+expression.ToString()+" "+ex.Message);
  640. }
  641. }
  642. public static Type GetPropertyOrFieldType(MemberInfo propertyOrField)
  643. {
  644. if (propertyOrField.MemberType == MemberTypes.Property)
  645. return ((PropertyInfo)propertyOrField).PropertyType;
  646. if (propertyOrField.MemberType == MemberTypes.Field)
  647. return ((FieldInfo)propertyOrField).FieldType;
  648. throw new NotSupportedException();
  649. }
  650. public static bool IsEntity(Type type)
  651. {
  652. return type.IsClass() && type != UtilConstants.StringType;
  653. }
  654. public static bool IsValueType(Type type)
  655. {
  656. return !IsEntity(type);
  657. }
  658. public static bool IsUnConvertExpress(Expression item)
  659. {
  660. return item is UnaryExpression && item.NodeType == ExpressionType.Convert;
  661. }
  662. internal static List<NewExpressionInfo> GetNewexpressionInfos(Expression item,ExpressionContext context, BaseResolve baseResolve)
  663. {
  664. List<NewExpressionInfo> result = new List<NewExpressionInfo>();
  665. foreach (MemberBinding binding in ((MemberInitExpression)item).Bindings)
  666. {
  667. if (binding.BindingType != MemberBindingType.Assignment)
  668. {
  669. throw new NotSupportedException();
  670. }
  671. MemberAssignment memberAssignment = (MemberAssignment)binding;
  672. NewExpressionInfo additem = new NewExpressionInfo();
  673. if (memberAssignment.Expression is MemberExpression)
  674. {
  675. additem.LeftNameName = memberAssignment.Member.Name;
  676. var member = (memberAssignment.Expression as MemberExpression).Expression;
  677. additem.ShortName = member + "";
  678. additem.RightName = (memberAssignment.Expression as MemberExpression).Member.Name;
  679. additem.RightDbName = context.GetDbColumnName(member.Type.Name, additem.RightName);
  680. if(ExpressionTool.IsNavMember(context, member))
  681. {
  682. additem.RightDbName=additem.RightName = baseResolve.GetNewExpressionValue(memberAssignment.Expression);
  683. }
  684. result.Add(additem);
  685. }
  686. else if (memberAssignment.Expression is ConstantExpression)
  687. {
  688. var value = ((ConstantExpression)memberAssignment.Expression).Value;
  689. //var leftInfo = keys[i];
  690. additem.Type = nameof(ConstantExpression);
  691. additem.RightName = memberAssignment.Member.Name;
  692. additem.ShortName = memberAssignment.Member.Name;
  693. additem.RightName = memberAssignment.Member.Name;
  694. additem.LeftNameName = memberAssignment.Member.Name;
  695. additem.RightDbName = UtilMethods.GetSqlValue(value);
  696. //additem.Value = "";
  697. result.Add(additem);
  698. }
  699. else if (memberAssignment.Expression is MemberInitExpression|| memberAssignment.Expression is NewExpression)
  700. {
  701. var dic = ExpressionTool.GetNewExpressionItemList(memberAssignment.Expression);
  702. foreach (var kv in dic)
  703. {
  704. additem = new NewExpressionInfo();
  705. //var leftInfo = keys[i];
  706. additem.Type = nameof(NewExpression);
  707. additem.RightName = kv.Key;
  708. additem.ShortName = ExpressionTool.GetParameters(kv.Value).First().Name;
  709. additem.RightName = kv.Key;
  710. additem.LeftNameName = memberAssignment.Member.Name + "." + kv.Key;
  711. additem.RightDbName = kv.Key;
  712. //additem.Value = "";
  713. result.Add(additem);
  714. }
  715. }
  716. else
  717. {
  718. var value = baseResolve.GetNewExpressionValue(memberAssignment.Expression);
  719. //var leftInfo = keys[i];
  720. additem.Type = nameof(ConstantExpression);
  721. additem.RightName = memberAssignment.Member.Name;
  722. additem.ShortName = memberAssignment.Member.Name;
  723. additem.RightName = memberAssignment.Member.Name;
  724. additem.LeftNameName = memberAssignment.Member.Name;
  725. additem.RightDbName = value;
  726. //additem.Value = "";
  727. result.Add(additem);
  728. }
  729. }
  730. return result;
  731. }
  732. internal static List<NewExpressionInfo> GetNewDynamicexpressionInfos(Expression item, ExpressionContext context, BaseResolve baseResolve)
  733. {
  734. List<NewExpressionInfo> result = new List<NewExpressionInfo>();
  735. int i = 0;
  736. foreach (var binding in ((NewExpression)item).Arguments)
  737. {
  738. NewExpressionInfo additem = new NewExpressionInfo();
  739. var keys = ((NewExpression)item).Members;
  740. if (binding is MemberExpression)
  741. {
  742. var member = (MemberExpression)binding;
  743. var entityName = member.Expression?.Type?.Name;
  744. //var memberAssignment = binding;
  745. //NewExpressionInfo additem = new NewExpressionInfo();
  746. additem.RightName = member.Member.Name;
  747. additem.ShortName = member.Expression + "";
  748. additem.RightName = member.Member.Name;
  749. additem.RightDbName = context.GetDbColumnName(entityName, additem.RightName);
  750. additem.LeftNameName = member.Member.Name;
  751. //additem.Value = "";
  752. result.Add(additem);
  753. }
  754. else if (binding is ConstantExpression)
  755. {
  756. var value = ((ConstantExpression)binding).Value;
  757. var leftInfo = keys[i];
  758. additem.Type = nameof(ConstantExpression);
  759. additem.RightName = leftInfo.Name;
  760. additem.ShortName = leftInfo.Name;
  761. additem.RightName = leftInfo.Name;
  762. additem.LeftNameName = leftInfo.Name;
  763. additem.RightDbName = UtilMethods.GetSqlValue(value);
  764. //additem.Value = "";
  765. result.Add(additem);
  766. }
  767. else if (binding is MemberInitExpression || binding is NewExpression)
  768. {
  769. var dic = ExpressionTool.GetNewExpressionItemList(binding);
  770. foreach (var kv in dic)
  771. {
  772. additem = new NewExpressionInfo();
  773. //var leftInfo = keys[i];
  774. additem.Type = nameof(NewExpression);
  775. additem.RightName = kv.Key;
  776. additem.ShortName = ExpressionTool.GetParameters(kv.Value).First().Name;
  777. additem.RightName = kv.Key;
  778. additem.LeftNameName = keys[i].Name+ "." + kv.Key;
  779. additem.RightDbName = kv.Key;
  780. //additem.Value = "";
  781. result.Add(additem);
  782. }
  783. }
  784. else
  785. {
  786. var value = baseResolve.GetNewExpressionValue(binding);
  787. var leftInfo = keys[i];
  788. additem.Type = nameof(ConstantExpression);
  789. additem.RightName = leftInfo.Name;
  790. additem.ShortName = leftInfo.Name;
  791. additem.RightName = leftInfo.Name;
  792. additem.LeftNameName = leftInfo.Name;
  793. additem.RightDbName = value;
  794. //additem.Value = "";
  795. result.Add(additem);
  796. }
  797. i++;
  798. }
  799. return result;
  800. }
  801. internal static bool IsSubQuery(Expression it)
  802. {
  803. if (it is MethodCallExpression)
  804. {
  805. var method = (MethodCallExpression)it;
  806. if (method.Object != null && method.Object.Type.Name.StartsWith("Subquery"))
  807. {
  808. return true;
  809. }
  810. }
  811. return false;
  812. }
  813. internal static bool IsIsNullSubQuery(Expression it)
  814. {
  815. if (it is MethodCallExpression)
  816. {
  817. var method = (MethodCallExpression)it;
  818. if (method.Method.Name == "IsNull")
  819. {
  820. if (method.Arguments.Count==2&&IsSubQuery(method.Arguments[0]))
  821. {
  822. return true;
  823. }
  824. }
  825. }
  826. return false;
  827. }
  828. internal static bool IsMemberInit(object selectValue)
  829. {
  830. var result = false;
  831. if (selectValue is Expression)
  832. {
  833. if (selectValue is MemberInitExpression)
  834. {
  835. result = true;
  836. }
  837. else if (selectValue is LambdaExpression)
  838. {
  839. var lambda = (LambdaExpression)selectValue;
  840. if (lambda.Body is MemberInitExpression)
  841. {
  842. result = true;
  843. }
  844. }
  845. }
  846. return result;
  847. }
  848. internal static MemberInitExpression GetMemberInit(object selectValue)
  849. {
  850. MemberInitExpression result = null;
  851. if (selectValue is Expression)
  852. {
  853. if (selectValue is MemberInitExpression)
  854. {
  855. result = (MemberInitExpression)selectValue;
  856. }
  857. else if (selectValue is LambdaExpression)
  858. {
  859. var lambda = (LambdaExpression)selectValue;
  860. if (lambda.Body is MemberInitExpression)
  861. {
  862. result = (MemberInitExpression)lambda.Body;
  863. }
  864. }
  865. }
  866. return result;
  867. }
  868. public static bool IsNegate(Expression exp)
  869. {
  870. return exp is UnaryExpression && exp.NodeType == ExpressionType.Negate;
  871. }
  872. public static bool GetIsLength(Expression item)
  873. {
  874. var isLength=(item is MemberExpression) && ((item as MemberExpression).Member.Name == "Length");
  875. if (isLength)
  876. {
  877. var exp=(item as MemberExpression).Expression;
  878. if (exp == null)
  879. {
  880. return false;
  881. }
  882. else if (exp.Type == UtilConstants.StringType&&item.Type==UtilConstants.IntType)
  883. {
  884. return true;
  885. }
  886. else
  887. {
  888. return false;
  889. }
  890. }
  891. else
  892. {
  893. return false;
  894. }
  895. }
  896. }
  897. }