diff --git a/MicroRuleEngine/MRE.cs b/MicroRuleEngine/MRE.cs index 8117313..37bfa3b 100644 --- a/MicroRuleEngine/MRE.cs +++ b/MicroRuleEngine/MRE.cs @@ -42,14 +42,30 @@ public class MRE private static readonly Lazy _miDecimalTryParse = new Lazy(() => typeof(Decimal).GetMethod("TryParse", new Type[] { typeof(string), Type.GetType("System.Decimal&") })); + public Func CompileRule(Rule r) + { + return CompileRule(r, + true); + } + + + public Func CompileRule(Rule r, bool useTryCatchForNulls) { var paramUser = Expression.Parameter(typeof(T)); - Expression expr = GetExpressionForRule(typeof(T), r, paramUser); + Expression expr = GetExpressionForRule(typeof(T), r, paramUser, useTryCatchForNulls); return Expression.Lambda>(expr, paramUser).Compile(); } - public static Expression> ToExpression(Rule r, bool useTryCatchForNulls = true) + + + public static Expression> ToExpression(Rule r) + { + return ToExpression(r, + true); + } + + public static Expression> ToExpression(Rule r, bool useTryCatchForNulls) { var paramUser = Expression.Parameter(typeof(T)); Expression expr = GetExpressionForRule(typeof(T), r, paramUser, useTryCatchForNulls); @@ -57,47 +73,91 @@ public static Expression> ToExpression(Rule r, bool useTryCatch return Expression.Lambda>(expr, paramUser); } - public static Func ToFunc(Rule r, bool useTryCatchForNulls = true) + public static Func ToFunc(Rule r) + { + return ToFunc(r, + true); + } + + public static Func ToFunc(Rule r, bool useTryCatchForNulls) { return ToExpression(r, useTryCatchForNulls).Compile(); } - public static Expression> ToExpression(Type type, Rule r) + + public static Expression> ToExpression(Type type, + Rule r) + { + return ToExpression(type, + r, + true); + } + + public static Expression> ToExpression(Type type, Rule r, bool useTryCatchForNulls) { var paramUser = Expression.Parameter(typeof(object)); - Expression expr = GetExpressionForRule(type, r, paramUser); + Expression expr = GetExpressionForRule(type, r, paramUser, useTryCatchForNulls); return Expression.Lambda>(expr, paramUser); } - public static Func ToFunc(Type type, Rule r) + public static Func ToFunc(Type type, + Rule r) + { + return ToFunc(type, + r, + true); + } + + public static Func ToFunc(Type type, Rule r, bool useTryCatchForNulls) { - return ToExpression(type, r).Compile(); + return ToExpression(type, r, useTryCatchForNulls).Compile(); } - public Func CompileRule(Type type, Rule r) + public Func CompileRule(Type type, + Rule r) + { + return CompileRule(type, + r, + true); + } + + public Func CompileRule(Type type, Rule r, bool useTryCatchForNulls) { var paramUser = Expression.Parameter(typeof(object)); - Expression expr = GetExpressionForRule(type, r, paramUser); + Expression expr = GetExpressionForRule(type, r, paramUser, useTryCatchForNulls); return Expression.Lambda>(expr, paramUser).Compile(); } public Func CompileRules(IEnumerable rules) + { + return CompileRules(rules, + true); + } + + public Func CompileRules(IEnumerable rules, bool useTryCatchForNulls) { var paramUser = Expression.Parameter(typeof(T)); - var expr = BuildNestedExpression(typeof(T), rules, paramUser, ExpressionType.And); + var expr = BuildNestedExpression(typeof(T), rules, paramUser, ExpressionType.And, useTryCatchForNulls); return Expression.Lambda>(expr, paramUser).Compile(); } public Func CompileRules(Type type, IEnumerable rules) + { + return CompileRules(type, + rules, + true); + } + + public Func CompileRules(Type type, IEnumerable rules, bool useTryCatchForNulls) { var paramUser = Expression.Parameter(type); - var expr = BuildNestedExpression(type, rules, paramUser, ExpressionType.And); + var expr = BuildNestedExpression(type, rules, paramUser, ExpressionType.And, useTryCatchForNulls); return Expression.Lambda>(expr, paramUser).Compile(); } // Build() in some forks - protected static Expression GetExpressionForRule(Type type, Rule rule, ParameterExpression parameterExpression, bool useTryCatchForNulls = true) + protected static Expression GetExpressionForRule(Type type, Rule rule, ParameterExpression parameterExpression, bool useTryCatchForNulls) { ExpressionType nestedOperator; if (ExpressionType.TryParse(rule.Operator, out nestedOperator) && @@ -201,9 +261,9 @@ private static Expression GetProperty(Expression param, string propname) } private static Expression BuildEnumerableOperatorExpression(Type type, Rule rule, - ParameterExpression parameterExpression) + ParameterExpression parameterExpression, bool useTryCatchForNulls = true) { - var collectionPropertyExpression = BuildExpr(type, rule, parameterExpression); + var collectionPropertyExpression = BuildExpr(type, rule, parameterExpression, useTryCatchForNulls); var itemType = GetCollectionItemType(collectionPropertyExpression.Type); var expressionParameter = Expression.Parameter(itemType); @@ -211,7 +271,7 @@ private static Expression BuildEnumerableOperatorExpression(Type type, Rule rule var genericFunc = typeof(Func<,>).MakeGenericType(itemType, typeof(bool)); - var innerExp = BuildNestedExpression(itemType, rule.Rules, expressionParameter, ExpressionType.And); + var innerExp = BuildNestedExpression(itemType, rule.Rules, expressionParameter, ExpressionType.And, useTryCatchForNulls); var predicate = Expression.Lambda(genericFunc, innerExp, expressionParameter); var body = Expression.Call(typeof(Enumerable), rule.Operator, new[] { itemType }, @@ -239,7 +299,7 @@ where string.Equals(oprator, tup.Item1, StringComparison.CurrentCultureIgnoreCas select tup.Item2.Value).FirstOrDefault(); } - private static Expression BuildExpr(Type type, Rule rule, Expression param, bool useTryCatch = true) + private static Expression BuildExpr(Type type, Rule rule, Expression param, bool useTryCatch) { Expression propExpression; Type propType; @@ -343,7 +403,7 @@ private static Expression BuildExpr(Type type, Rule rule, Expression param, bool ? Expression.Call(enumrOperation.MakeGenericMethod(elementType), propExpression, Expression.Lambda( - BuildNestedExpression(elementType, rule.Rules, lambdaParam, ExpressionType.AndAlso), + BuildNestedExpression(elementType, rule.Rules, lambdaParam, ExpressionType.AndAlso, useTryCatch), lambdaParam)