public override EntityQueryModelVisitor Create(QueryCompilationContext queryCompilationContext,
     EntityQueryModelVisitor parentEntityQueryModelVisitor)
     => new MyEntityQueryModelVisitor(QueryOptimizer,
         NavigationRewritingExpressionVisitorFactory,
         SubQueryMemberPushDownExpressionVisitor,
         QuerySourceTracingExpressionVisitorFactory,
         EntityResultFindingExpressionVisitorFactory,
         TaskBlockingExpressionVisitor,
         MemberAccessBindingExpressionVisitorFactory,
         OrderingExpressionVisitorFactory,
         ProjectionExpressionVisitorFactory,
         EntityQueryableExpressionVisitorFactory,
         QueryAnnotationExtractor,
         ResultOperatorHandler,
         EntityMaterializerSource,
         ExpressionPrinter,
         queryCompilationContext);
 /// <summary>
 /// 构造函数
 /// </summary>
 /// <param name="dependencies"></param>
 /// <param name="relationalDependencies"></param>
 /// <param name="queryCompilationContext"></param>
 public SqlServer2008QueryTranslationPostprocessor(QueryTranslationPostprocessorDependencies dependencies, RelationalQueryTranslationPostprocessorDependencies relationalDependencies, QueryCompilationContext queryCompilationContext)
     : base(dependencies, relationalDependencies, queryCompilationContext)
 {
 }
Beispiel #3
0
        public override void VisitAdditionalFromClause(
            AdditionalFromClause fromClause, QueryModel queryModel, int index)
        {
            Check.NotNull(fromClause, nameof(fromClause));
            Check.NotNull(queryModel, nameof(queryModel));

            base.VisitAdditionalFromClause(fromClause, queryModel, index);

            RequiresClientSelectMany = true;

            var selectExpression = TryGetQuery(fromClause);

            if (selectExpression != null &&
                selectExpression.Tables.Count == 1)
            {
                var previousQuerySource = FindPreviousQuerySource(queryModel, index);

                if (previousQuerySource != null &&
                    !RequiresClientJoin)
                {
                    var previousSelectExpression = TryGetQuery(previousQuerySource);

                    if (previousSelectExpression != null)
                    {
                        if (!QueryCompilationContext.QuerySourceRequiresMaterialization(previousQuerySource))
                        {
                            previousSelectExpression.ClearProjection();
                            previousSelectExpression.IsProjectStar = false;
                        }

                        var readerOffset = previousSelectExpression.Projection.Count;

                        var correlated = selectExpression.IsCorrelated();

                        if (correlated)
                        {
                            if (!QueryCompilationContext.IsLateralJoinSupported)
                            {
                                return;
                            }

                            previousSelectExpression
                            .AddLateralJoin(selectExpression.Tables.First(), selectExpression.Projection);
                        }
                        else
                        {
                            previousSelectExpression
                            .AddCrossJoin(selectExpression.Tables.First(), selectExpression.Projection);
                        }

                        QueriesBySource.Remove(fromClause);

                        Expression
                            = _queryFlattenerFactory
                              .Create(
                                  fromClause,
                                  QueryCompilationContext,
                                  LinqOperatorProvider.SelectMany,
                                  readerOffset)
                              .Flatten((MethodCallExpression)Expression);

                        RequiresClientSelectMany = false;
                    }
                }
            }

            if (RequiresClientSelectMany)
            {
                CheckClientEval(fromClause);
            }
        }
Beispiel #4
0
        protected virtual void OptimizeJoinClause(
            [NotNull] JoinClause joinClause,
            [NotNull] QueryModel queryModel,
            int index,
            [NotNull] Action baseVisitAction,
            [NotNull] MethodInfo operatorToFlatten,
            bool outerJoin = false)
        {
            Check.NotNull(joinClause, nameof(joinClause));
            Check.NotNull(queryModel, nameof(queryModel));
            Check.NotNull(baseVisitAction, nameof(baseVisitAction));
            Check.NotNull(operatorToFlatten, nameof(operatorToFlatten));

            RequiresClientJoin = true;

            var previousQuerySource = FindPreviousQuerySource(queryModel, index);

            var previousSelectExpression
                = previousQuerySource != null
                    ? TryGetQuery(previousQuerySource)
                    : null;

            var previousSelectProjectionCount
                = previousSelectExpression?.Projection.Count ?? -1;

            baseVisitAction();

            if (previousSelectExpression != null)
            {
                var selectExpression = TryGetQuery(joinClause);

                if (selectExpression != null)
                {
                    var sqlTranslatingExpressionVisitor
                        = _sqlTranslatingExpressionVisitorFactory.Create(this);

                    var predicate
                        = sqlTranslatingExpressionVisitor
                          .Visit(
                              Expression.Equal(
                                  joinClause.OuterKeySelector,
                                  joinClause.InnerKeySelector));

                    if (predicate != null)
                    {
                        QueriesBySource.Remove(joinClause);

                        previousSelectExpression.RemoveRangeFromProjection(previousSelectProjectionCount);

                        var tableExpression = selectExpression.Tables.Single();

                        var projection
                            = QueryCompilationContext
                              .QuerySourceRequiresMaterialization(joinClause)
                                ? selectExpression.Projection
                                : Enumerable.Empty <Expression>();

                        var joinExpression
                            = !outerJoin
                                ? previousSelectExpression.AddInnerJoin(tableExpression, projection)
                                : previousSelectExpression.AddLeftOuterJoin(tableExpression, projection);

                        joinExpression.Predicate = predicate;

                        if (outerJoin)
                        {
                            var outerJoinOrderingExtractor = new OuterJoinOrderingExtractor();

                            outerJoinOrderingExtractor.Visit(predicate);

                            foreach (var expression in outerJoinOrderingExtractor.Expressions)
                            {
                                previousSelectExpression
                                .AddToOrderBy(new Ordering(expression, OrderingDirection.Asc));
                            }
                        }

                        Expression
                            = _queryFlattenerFactory
                              .Create(
                                  joinClause,
                                  QueryCompilationContext,
                                  operatorToFlatten,
                                  previousSelectProjectionCount)
                              .Flatten((MethodCallExpression)Expression);

                        RequiresClientJoin = false;
                    }
                }
            }

            if (RequiresClientJoin)
            {
                CheckClientEval(joinClause);
            }
        }
Beispiel #5
0
 /// <summary>
 ///     Creates a new <see cref="EntityQueryModelVisitor" />.
 /// </summary>
 /// <param name="queryCompilationContext">
 ///     Compilation context for the query.
 /// </param>
 /// <param name="parentEntityQueryModelVisitor">
 ///     The visitor for the outer query.
 /// </param>
 /// <returns> The new created visitor. </returns>
 public abstract EntityQueryModelVisitor Create(
     QueryCompilationContext queryCompilationContext,
     EntityQueryModelVisitor parentEntityQueryModelVisitor);
Beispiel #6
0
 public virtual QueryOptimizer Create(QueryCompilationContext queryCompilationContext)
 => new QueryOptimizer(Dependencies, queryCompilationContext);
Beispiel #7
0
 public QueryOptimizer(QueryCompilationContext queryCompilationContext)
 {
     _queryCompilationContext = queryCompilationContext;
 }
 /// <summary>
 ///     Creates a new <see cref="EntityQueryModelVisitor"/>.
 /// </summary>
 /// <param name="queryCompilationContext">
 ///     Compilation context for the query.
 /// </param>
 /// <param name="parentEntityQueryModelVisitor">
 ///     The visitor for the outer query.
 /// </param>
 /// <returns> The new created visitor. </returns>
 public abstract EntityQueryModelVisitor Create(
     QueryCompilationContext queryCompilationContext,
     EntityQueryModelVisitor parentEntityQueryModelVisitor);
 /// <summary>
 ///     Creates a new EntityQueryModelVisitor.
 /// </summary>
 /// <param name="queryCompilationContext"> Compilation context for the query. </param>
 /// <param name="parentEntityQueryModelVisitor"> The visitor for the outer query. </param>
 /// <returns>
 ///     An EntityQueryModelVisitor.
 /// </returns>
 public override EntityQueryModelVisitor Create(
     QueryCompilationContext queryCompilationContext,
     EntityQueryModelVisitor parentEntityQueryModelVisitor)
     => new RelationalQueryModelVisitor(
         QueryOptimizer,
         NavigationRewritingExpressionVisitorFactory,
         SubQueryMemberPushDownExpressionVisitor,
         QuerySourceTracingExpressionVisitorFactory,
         EntityResultFindingExpressionVisitorFactory,
         TaskBlockingExpressionVisitor,
         MemberAccessBindingExpressionVisitorFactory,
         OrderingExpressionVisitorFactory,
         ProjectionExpressionVisitorFactory,
         EntityQueryableExpressionVisitorFactory,
         QueryAnnotationExtractor,
         ResultOperatorHandler,
         EntityMaterializerSource,
         ExpressionPrinter,
         RelationalAnnotationProvider,
         IncludeExpressionVisitorFactory,
         SqlTranslatingExpressionVisitorFactory,
         CompositePredicateExpressionVisitorFactory,
         ConditionalRemovingExpressionVisitorFactory,
         QueryFlattenerFactory,
         ContextOptions,
         (RelationalQueryCompilationContext)Check.NotNull(queryCompilationContext, nameof(queryCompilationContext)),
         (RelationalQueryModelVisitor)parentEntityQueryModelVisitor);