private Expression ParameterizeQuery(Expression expression, QueryProcessingContext context)
        {
            // Parameterize the expression by substituting any ConstantExpression
            // that is not a literal constant (such as a closure instance) with a ParameterExpression.

            return(new ConstantParameterizingExpressionVisitor(context.ParameterMapping).Visit(expression));
        }
        private Func <object[], object> CompileDelegate(Expression expression, QueryProcessingContext context)
        {
            var parameters = new ParameterExpression[context.ParameterMapping.Count + 1];

            parameters[0] = context.ExecutionContextParameter;

            context.ParameterMapping.Values.CopyTo(parameters, 1);

            var parameterArray = Expression.Parameter(typeof(object[]));

            // Wrap the actual lambda in a static invocation.
            // This is faster than just compiling it and calling DynamicInvoke.

            return(Expression
                   .Lambda <Func <object[], object> >(
                       Expression.Convert(
                           Expression.Invoke(
                               Expression.Lambda(expression, parameters),
                               parameters.Select((p, i) =>
                                                 Expression.Convert(
                                                     Expression.ArrayIndex(
                                                         parameterArray,
                                                         Expression.Constant(i)),
                                                     p.Type))),
                           typeof(object)),
                       parameterArray)
                   .Compile());
        }
        private Expression InlineQuery(Expression expression, QueryProcessingContext context)
        {
            // Partially evaluate the expression. In addition to reducing evaluable nodes such
            // as `new DateTime(2000, 01, 01)` down to ConstantExpressions, this visitor also expands
            // IQueryable-producing expressions such as those found within calls to SelectMany
            // so that the resulting IQueryable's expression tree will be integrated into the
            // current expression tree.

            return(queryableInliningExpressionVisitorFactory.Create(context).Visit(expression));
        }
 public virtual IEnumerable <ExpressionVisitor> CreateExpressionVisitors(QueryProcessingContext context)
 {
     yield return(new QueryCompilingExpressionVisitor(
                      translatabilityAnalyzingExpressionVisitor,
                      queryTranslatingExpressionVisitorFactory,
                      new MaterializerGeneratingExpressionVisitor(
                          translatabilityAnalyzingExpressionVisitor,
                          readValueExpressionFactoryProvider),
                      context.ExecutionContextParameter));
 }
        public IEnumerable <ExpressionVisitor> CreateExpressionVisitors(QueryProcessingContext context)
        {
            yield return(new ConditionalComparisonOptimizingExpressionVisitor());

            yield return(new SelectorPushdownExpressionVisitor());

            yield return(new RedundantConversionStrippingExpressionVisitor());

            yield return(new NullOrDefaultEqualityOptimizingExpressionVisitor());

            yield return(new BooleanOptimizingExpressionVisitor());
        }
Exemplo n.º 6
0
        public virtual IEnumerable <ExpressionVisitor> CreateExpressionVisitors(QueryProcessingContext context)
        {
            yield return(new KeyEqualityComposingExpressionVisitor(context.DescriptorSet));

            yield return(new NavigationComposingExpressionVisitor(context.DescriptorSet.NavigationDescriptors));

            yield return(new TableAliasComposingExpressionVisitor());

            yield return(new QueryComposingExpressionVisitor(
                             translatabilityAnalyzingExpressionVisitor,
                             rewritingExpressionVisitorProvider.CreateExpressionVisitors(context),
                             new SqlParameterRewritingExpressionVisitor(context.ParameterMapping.Values)));
        }
Exemplo n.º 7
0
        public virtual IEnumerable <ExpressionVisitor> CreateExpressionVisitors(QueryProcessingContext context)
        {
            yield return(new SqlServerObjectToStringRewritingExpressionVisitor());

            yield return(new SqlServerStringToNumberAsciiRewritingExpressionVisitor());

            yield return(new SqlServerCountRewritingExpressionVisitor());

            yield return(new SqlServerMathMethodRewritingExpressionVisitor());

            yield return(new SqlServerJsonMemberRewritingExpressionVisitor());

            yield return(new SqlServerStringJoinRewritingExpressionVisitor(context));
        }
        private Expression ApplyVisitors(Expression expression, QueryProcessingContext context)
        {
            var composingExpressionVisitors
                = composingExpressionVisitorProvider
                  .CreateExpressionVisitors(context)
                  .ToArray();

            var optimizingExpressionVisitors
                = optimizingExpressionVisitorProvider
                  .CreateExpressionVisitors(context)
                  .ToArray();

            var compilingExpressionVisitors
                = compilingExpressionVisitorProvider
                  .CreateExpressionVisitors(context)
                  .ToArray();

            // Apply all optimizing visitors before each composing visitor and then apply all
            // optimizing visitors one last time.

            foreach (var optimizingVisitor in optimizingExpressionVisitors)
            {
                expression = optimizingVisitor.Visit(expression);
            }

            foreach (var composingVisitor in composingExpressionVisitors)
            {
                expression = composingVisitor.Visit(expression);

                foreach (var optimizingVisitor in optimizingExpressionVisitors)
                {
                    expression = optimizingVisitor.Visit(expression);
                }
            }

            // Transform the expression by rewriting all composed query expressions into
            // executable expressions that make database calls and perform result materialization.

            foreach (var compilingVisitor in compilingExpressionVisitors)
            {
                expression = compilingVisitor.Visit(expression);
            }

            return(expression);
        }
Exemplo n.º 9
0
        public virtual IEnumerable <ExpressionVisitor> CreateExpressionVisitors(QueryProcessingContext context)
        {
            /*
             *
             * Order-dependency notes:
             *
             * - ListContainsToEnumerableContainsRewritingExpressionVisitor
             *  - has to run before EnumerableContainsRewritingExpressionVisitor
             *
             * - GroupingAggregationRewritingExpressionVisitor
             *  - has to run before the QueryComposingExpressionVisitor recurses
             *
             * - SqlServerStringJoinRewritingExpressionVisitor
             *  - has to run after the QueryComposingExpressionVisitor recurses
             *
             * Ideally none of these would be order-dependent beyond running before
             * or after the QueryComposingExpressionVisitor recurses.
             *
             */

            yield return(new ListContainsToEnumerableContainsRewritingExpressionVisitor());

            yield return(new EqualsMethodRewritingExpressionVisitor());

            yield return(new KeyEqualityRewritingExpressionVisitor(context.DescriptorSet));

            yield return(new GroupingAggregationRewritingExpressionVisitor(translatabilityAnalyzingExpressionVisitor));

            yield return(new TypeBinaryExpressionRewritingExpressionVisitor());

            yield return(new NullableMemberRewritingExpressionVisitor());

            yield return(new DateTimeMemberRewritingExpressionVisitor());

            yield return(new StringMemberRewritingExpressionVisitor());

            yield return(new CollectionContainsRewritingExpressionVisitor());

            yield return(new EnumerableContainsRewritingExpressionVisitor());

            yield return(new EnumerableQueryEqualityRewritingExpressionVisitor());

            yield return(new EnumHasFlagRewritingExpressionVisitor(typeMappingProvider));
        }
        public virtual IEnumerable <ExpressionVisitor> CreateExpressionVisitors(QueryProcessingContext context)
        {
            // 'Simple' replacement rewriters

            yield return(new ListContainsToEnumerableContainsRewritingExpressionVisitor());

            yield return(new EqualsMethodRewritingExpressionVisitor());

            // 'Core' rewriters

            yield return(new KeyEqualityRewritingExpressionVisitor(context.DescriptorSet));

            yield return(new GroupingAggregationRewritingExpressionVisitor(translatabilityAnalyzingExpressionVisitor));

            yield return(new TypeBinaryExpressionRewritingExpressionVisitor());

            yield return(new NullableMemberRewritingExpressionVisitor());

            yield return(new DateTimeMemberRewritingExpressionVisitor());

            yield return(new StringMemberRewritingExpressionVisitor());

            yield return(new CollectionContainsRewritingExpressionVisitor());

            yield return(new EnumerableContainsRewritingExpressionVisitor());

            yield return(new EnumerableQueryEqualityRewritingExpressionVisitor());

            // SQL Server specific rewriters (should be pulled from the default provider at some point)

            yield return(new ObjectToStringRewritingExpressionVisitor());

            yield return(new StringToNumberAsciiRewritingExpressionVisitor());

            yield return(new SqlServerCountRewritingExpressionVisitor());

            yield return(new SqlServerMathMethodRewritingExpressionVisitor());

            yield return(new SqlServerJsonMemberRewritingExpressionVisitor());
        }
        private int ComputeHash(Expression expression, QueryProcessingContext context)
        {
            // Generate a hash code for the parameterized expression.
            // Because the expression is parameterized, the hash code will be identical
            // for expressions that are structurally equivalent apart from any closure instances.

            var comparer = ExpressionEqualityComparer.Instance;

            var hash = comparer.GetHashCode(expression);

            // Some parameters may have been eliminated during query inlining,
            // so we need to make sure all of our parameters' types are included
            // in the hash code to avoid errors related to mismatched closure types.

            unchecked
            {
                foreach (var parameter in context.ParameterMapping.Values)
                {
                    hash = (hash * 16777619) ^ comparer.GetHashCode(parameter);
                }
            }

            return(hash);
        }
 public QueryableInliningExpressionVisitor Create(QueryProcessingContext context)
 {
     return(new QueryableInliningExpressionVisitor(context.QueryProvider, context.ParameterMapping));
 }