Ejemplo n.º 1
0
        /// <summary>Parse one of the literals of skip token.</summary>
        /// <param name="literal">Input literal.</param>
        /// <returns>Object resulting from conversion of literal.</returns>
        internal static object ParseSkipTokenLiteral(string literal)
        {
            ExpressionLexer l = new ExpressionLexer(literal);
            ConstantNode    node;

            if (!TokenToQueryNodeTranslator.TryCreateLiteral(l.CurrentToken, out node))
            {
                throw new InvalidOperationException(ServiceStrings.RequsetQueryParser_ExpectingLiteralInSkipToken(literal));
            }

            return(node.Value);
        }
Ejemplo n.º 2
0
        /// <summary>Makes the expression that is used as a filter corresponding to skip token.</summary>
        /// <param name="topLevelOrderingInfo">Ordering expression.</param>
        /// <param name="skipToken">The provided skip token.</param>
        /// <param name="parameterType">The parameter type of the lambda.</param>
        /// <returns>LambdaExpression corresponding to the skip token filter.</returns>
        internal LambdaExpression BuildSkipTokenFilter(OrderingInfo topLevelOrderingInfo, IList <object> skipToken, Type parameterType)
        {
            ParameterExpression element       = Expression.Parameter(parameterType, "element");
            Expression          lastCondition = Expression.Constant(true, typeof(bool));
            Expression          lastMatch     = Expression.Constant(false, typeof(bool));

            foreach (var v in WebUtil.Zip(topLevelOrderingInfo.OrderingExpressions, skipToken, (x, y) => new { Order = x, Value = y }))
            {
                BinaryOperatorKind comparisonExp = v.Order.IsAscending ? BinaryOperatorKind.GreaterThan : BinaryOperatorKind.LessThan;

                Expression fixedLambda = ParameterReplacerVisitor.Replace(
                    ((LambdaExpression)v.Order.Expression).Body,
                    ((LambdaExpression)v.Order.Expression).Parameters[0],
                    element);

                // TODO: this will be an EnumNode if $skiptoken contains enum constant.
                ConstantNode node;
                var          lexer   = new ExpressionLexer((string)v.Value);
                bool         success = TokenToQueryNodeTranslator.TryCreateLiteral(lexer.CurrentToken, out node);
                Debug.Assert(success, "Was not a literal");

                node = this.EnsureCorrectTypeAndPrecisionForLFDM(node, fixedLambda.Type);
                Expression right      = this.nodeToExpressionTranslator.TranslateNode(node);
                Expression comparison = ExpressionGenerator.GenerateLogicalAnd(
                    lastCondition,
                    this.GenerateNullAwareComparison(fixedLambda, right, comparisonExp));

                lastMatch = ExpressionGenerator.GenerateLogicalOr(lastMatch, comparison);

                lastCondition = ExpressionGenerator.GenerateLogicalAnd(
                    lastCondition,
                    this.GenerateComparisonExpression(fixedLambda, right, BinaryOperatorKind.Equal));
            }

            lastMatch = ExpressionUtils.EnsurePredicateExpressionIsBoolean(lastMatch);

            Debug.Assert(lastMatch.Type == typeof(bool), "Skip token should generate boolean expression.");

            return(Expression.Lambda(lastMatch, element));
        }