private IFieldFilter AddFieldFilter(string name, object value, ComparisonConstants comparsion)
        {
            //handle enums
            if (value != null)
            {
                if (value.GetType().BaseType.FullName == "System.Enum")
                {
                    value = Convert.ToInt32(value);
                }
            }

            var filter = (IFieldFilter) new FieldFilter();

            filter.Comparer = comparsion;
            filter.Name     = name;
            filter.Value    = value;

            if (FieldFilters == null)
            {
                FieldFilters = new List <IFieldFilter>();
            }

            //if (this.FieldFilters.FindIndex(x => x.Name == filter.Name) >= 0)
            //    throw new InvalidOperationException($"Duplicate filter field \"{filter.Name}\" was encountered.");

            FieldFilters.Add(filter);
            return(filter);
        }
        private bool ParseExpression(MemberExpression memberExpr, Expression valueExpr, ComparisonConstants comparison)
        {
            try
            {
                if (memberExpr == null)
                {
                    return(false);
                }

                var constantExpr = valueExpr as ConstantExpression;
                if (constantExpr != null)
                {
                    AddFieldFilter(memberExpr.Member.Name, constantExpr.Value, comparison);
                    return(true);
                }

                // This is kinda of weird the compiler creates an object for the variables in a where conditions
                // For example, Where(x => x.Category != f)

                var memberAccessValueExpr = valueExpr as MemberExpression;
                if (memberAccessValueExpr != null)
                {
                    var theValue = ExpressionHelper.GetMemberExpressionValue(memberAccessValueExpr);
                    AddFieldFilter(memberExpr.Member.Name, theValue, comparison);
                    return(true);
                }

                var unaryExpressionExpr = valueExpr as UnaryExpression;
                if (unaryExpressionExpr != null)
                {
                    var theValue = ExpressionHelper.GetMemberExpressionValue(unaryExpressionExpr);
                    AddFieldFilter(memberExpr.Member.Name, theValue, comparison);
                    return(true);
                }

                var methodExpressionExpr = valueExpr as MethodCallExpression;
                if (methodExpressionExpr != null)
                {
                    //Parse DateTime functions like AddDays, etc.
                    //if (methodExpressionExpr.Method.DeclaringType.FullName == "System.DateTime")
                    {
                        var objectMember = Expression.Convert(methodExpressionExpr, typeof(object));
                        var getterLambda = Expression.Lambda <Func <object> >(objectMember);
                        var getter       = getterLambda.Compile();
                        var theValue     = getter();
                        AddFieldFilter(memberExpr.Member.Name, theValue, comparison);
                        return(true);
                    }
                }

                return(false);
            }
            catch (Exception ex)
            {
                LoggerCQ.LogError(ex);
                return(false);
            }
        }
        private void ParseExpression(BinaryExpression expression, ComparisonConstants comparison)
        {
            // Handles Where(x => X.Field == 5); Or
            // Handles Where(x => 5 == X.Field); Or
            // Handles Where(x => X.Field == variable); Or
            // Handles Where(x => variable == X.Field);

            var leftExpr  = expression.Left;
            var rightExpr = expression.Right;

            #region Setup Left/Right
            //If a value and property are different nullable/not nullable there is a convert done so get the real memeber expression
            var convertPropertyExpr = leftExpr as UnaryExpression;
            if (convertPropertyExpr != null && convertPropertyExpr.NodeType == ExpressionType.Convert)
            {
                var memExp = convertPropertyExpr.Operand as MemberExpression;
                if (memExp != null)
                {
                    leftExpr = memExp;
                }
            }
            convertPropertyExpr = rightExpr as UnaryExpression;
            if (convertPropertyExpr != null && convertPropertyExpr.NodeType == ExpressionType.Convert)
            {
                var memExp = convertPropertyExpr.Operand as MemberExpression;
                if (memExp != null)
                {
                    rightExpr = memExp;
                }
            }
            #endregion

            if (!ParseExpression(leftExpr as MemberExpression, rightExpr, comparison))
            {
                //we are flipping this equaltion so flip the comparer
                //i.e. 1<X => X>1
                var newComp = comparison;
                switch (comparison)
                {
                case ComparisonConstants.GreaterThan:
                    newComp = ComparisonConstants.LessThan;
                    break;

                case ComparisonConstants.GreaterThanOrEq:
                    newComp = ComparisonConstants.LessThanOrEq;
                    break;

                case ComparisonConstants.LessThan:
                    newComp = ComparisonConstants.GreaterThan;
                    break;

                case ComparisonConstants.LessThanOrEq:
                    newComp = ComparisonConstants.GreaterThanOrEq;
                    break;
                }

                if (!ParseExpression(rightExpr as MemberExpression, leftExpr, newComp))
                {
                    throw new InvalidOperationException("Invalid where condition expression.");
                }
            }
        }