Beispiel #1
0
        private async Task InitializeFeedContinuationAsync(CancellationToken cancellationToken)
        {
            Routing.PartitionKeyRangeCache partitionKeyRangeCache = await this.clientContext.DocumentClient.GetPartitionKeyRangeCacheAsync();

            List <Documents.Routing.Range <string> > ranges;

            if (this.FeedRangeInternal is FeedRangePartitionKey)
            {
                Documents.PartitionKeyDefinition partitionKeyDefinition = await this.container.GetPartitionKeyDefinitionAsync(cancellationToken);

                ranges = await this.FeedRangeInternal.GetEffectiveRangesAsync(partitionKeyRangeCache, this.lazyContainerRid.Result.Result, partitionKeyDefinition);
            }
            else
            {
                IReadOnlyList <Documents.PartitionKeyRange> pkRanges = await partitionKeyRangeCache.TryGetOverlappingRangesAsync(
                    collectionRid : this.lazyContainerRid.Result.Result,
                    range : (this.FeedRangeInternal as FeedRangeEPK).Range,
                    forceRefresh : false);

                ranges = pkRanges.Select(pkRange => pkRange.ToRange()).ToList();
            }

            this.FeedRangeContinuation = new FeedRangeCompositeContinuation(
                containerRid: this.lazyContainerRid.Result.Result,
                feedRange: this.FeedRangeInternal,
                ranges: ranges);
        }
Beispiel #2
0
        public static Task<PartitionedQueryExecutionInfo> GetQueryPlanWithServiceInteropAsync(
            CosmosQueryClient queryClient,
            SqlQuerySpec sqlQuerySpec,
            PartitionKeyDefinition partitionKeyDefinition,
            bool hasLogicalPartitionKey,
            CancellationToken cancellationToken = default(CancellationToken))
        {
            if (queryClient == null)
            {
                throw new ArgumentNullException(nameof(queryClient));
            }

            if (sqlQuerySpec == null)
            {
                throw new ArgumentNullException(nameof(sqlQuerySpec));
            }

            if (partitionKeyDefinition == null)
            {
                throw new ArgumentNullException(nameof(partitionKeyDefinition));
            }

            cancellationToken.ThrowIfCancellationRequested();
            QueryPlanHandler queryPlanHandler = new QueryPlanHandler(queryClient);

            return queryPlanHandler.GetQueryPlanAsync(
                    sqlQuerySpec,
                    partitionKeyDefinition,
                    QueryPlanRetriever.SupportedQueryFeatures,
                    hasLogicalPartitionKey,
                    cancellationToken);
        }
Beispiel #3
0
 public abstract Task <List <Documents.PartitionKeyRange> > GetTargetPartitionKeyRangeByFeedRangeAsync(
     string resourceLink,
     string collectionResourceId,
     Documents.PartitionKeyDefinition partitionKeyDefinition,
     FeedRangeInternal feedRangeInternal,
     bool forceRefresh,
     ITrace trace);
Beispiel #4
0
        public async Task <PartitionedQueryExecutionInfo> GetQueryPlanAsync(
            SqlQuerySpec sqlQuerySpec,
            PartitionKeyDefinition partitionKeyDefinition,
            QueryFeatures supportedQueryFeatures,
            bool hasLogicalPartitionKey,
            CancellationToken cancellationToken)
        {
            cancellationToken.ThrowIfCancellationRequested();

            if (sqlQuerySpec == null)
            {
                throw new ArgumentNullException($"{nameof(sqlQuerySpec)}");
            }

            if (partitionKeyDefinition == null)
            {
                throw new ArgumentNullException($"{nameof(partitionKeyDefinition)}");
            }

            PartitionedQueryExecutionInfo partitionedQueryExecutionInfo = await this.GetQueryInfoAsync(
                sqlQuerySpec,
                partitionKeyDefinition,
                hasLogicalPartitionKey,
                cancellationToken);

            QueryPlanHandler.QueryPlanExceptionFactory.ThrowIfNotSupported(
                partitionedQueryExecutionInfo.QueryInfo,
                supportedQueryFeatures);

            return(partitionedQueryExecutionInfo);
        }
        public override async Task <List <Documents.Routing.Range <string> > > GetEffectiveRangesAsync(
            IRoutingMapProvider routingMapProvider,
            string containerRid,
            Documents.PartitionKeyDefinition partitionKeyDefinition)
        {
            Documents.PartitionKeyRange pkRange = await routingMapProvider.TryGetPartitionKeyRangeByIdAsync(
                collectionResourceId : containerRid,
                partitionKeyRangeId : this.PartitionKeyRangeId,
                forceRefresh : false);

            if (pkRange == null)
            {
                // Try with a refresh
                pkRange = await routingMapProvider.TryGetPartitionKeyRangeByIdAsync(
                    collectionResourceId : containerRid,
                    partitionKeyRangeId : this.PartitionKeyRangeId,
                    forceRefresh : true);
            }

            if (pkRange == null)
            {
                throw new InvalidOperationException($"The PartitionKeyRangeId: \"{this.PartitionKeyRangeId}\" is not valid for the current container {containerRid} .");
            }

            return(new List <Documents.Routing.Range <string> > {
                pkRange.ToRange()
            });
        }
Beispiel #6
0
        /// <summary>
        /// Used in the compute gateway to support legacy gateways query execution pattern.
        /// </summary>
        public async Task <(PartitionedQueryExecutionInfo, bool)> GetQueryInfoAndIfSupportedAsync(
            QueryFeatures supportedQueryFeatures,
            SqlQuerySpec sqlQuerySpec,
            PartitionKeyDefinition partitionKeyDefinition,
            bool hasLogicalPartitionKey,
            CancellationToken cancellationToken = default(CancellationToken))
        {
            if (sqlQuerySpec == null)
            {
                throw new ArgumentNullException(nameof(sqlQuerySpec));
            }

            if (partitionKeyDefinition == null)
            {
                throw new ArgumentNullException(nameof(partitionKeyDefinition));
            }

            cancellationToken.ThrowIfCancellationRequested();

            PartitionedQueryExecutionInfo partitionedQueryExecutionInfo = await this.GetQueryInfoAsync(
                sqlQuerySpec,
                partitionKeyDefinition,
                hasLogicalPartitionKey,
                cancellationToken);

            QueryFeatures neededQueryFeatures = QueryPlanSupportChecker.GetNeededQueryFeatures(
                partitionedQueryExecutionInfo.QueryInfo,
                supportedQueryFeatures);

            return(partitionedQueryExecutionInfo, neededQueryFeatures == QueryFeatures.None);
        }
Beispiel #7
0
        public async Task FeedRangePK_GetPartitionKeyRangesAsync()
        {
            Documents.Routing.Range <string> range             = new Documents.Routing.Range <string>("AA", "BB", true, false);
            Documents.PartitionKeyRange      partitionKeyRange = new Documents.PartitionKeyRange()
            {
                Id = Guid.NewGuid().ToString(), MinInclusive = range.Min, MaxExclusive = range.Max
            };
            Documents.PartitionKeyDefinition partitionKeyDefinition = new Documents.PartitionKeyDefinition();
            partitionKeyDefinition.Paths.Add("/id");
            PartitionKey        partitionKey    = new PartitionKey("test");
            IRoutingMapProvider routingProvider = Mock.Of <IRoutingMapProvider>();

            Mock.Get(routingProvider)
            .Setup(f => f.TryGetOverlappingRangesAsync(It.IsAny <string>(), It.IsAny <Documents.Routing.Range <string> >(), It.IsAny <bool>()))
            .ReturnsAsync(new List <Documents.PartitionKeyRange>()
            {
                partitionKeyRange
            });

            FeedRangePartitionKey feedRangePartitionKey = new FeedRangePartitionKey(partitionKey);
            IEnumerable <string>  pkRanges = await feedRangePartitionKey.GetPartitionKeyRangesAsync(routingProvider, null, partitionKeyDefinition, default(CancellationToken));

            Assert.AreEqual(1, pkRanges.Count());
            Assert.AreEqual(partitionKeyRange.Id, pkRanges.First());
        }
Beispiel #8
0
 public override Task <List <Documents.Routing.Range <string> > > GetEffectiveRangesAsync(
     IRoutingMapProvider routingMapProvider,
     string containerRid,
     Documents.PartitionKeyDefinition partitionKeyDefinition) => Task.FromResult(new List <Documents.Routing.Range <string> >()
 {
     this.Range
 });
Beispiel #9
0
        private async Task <PartitionedQueryExecutionInfo> GetQueryInfoAsync(
            SqlQuerySpec sqlQuerySpec,
            PartitionKeyDefinition partitionKeyDefinition,
            bool hasLogicalPartitionKey,
            CancellationToken cancellationToken = default(CancellationToken))
        {
            cancellationToken.ThrowIfCancellationRequested();

            PartitionedQueryExecutionInfo partitionedQueryExecutionInfo = await this.queryClient
                                                                          .GetPartitionedQueryExecutionInfoAsync(
                sqlQuerySpec : sqlQuerySpec,
                partitionKeyDefinition : partitionKeyDefinition,
                requireFormattableOrderByQuery : true,
                isContinuationExpected : false,
                allowNonValueAggregateQuery : true,
                hasLogicalPartitionKey : hasLogicalPartitionKey,
                cancellationToken : cancellationToken);

            if (partitionedQueryExecutionInfo == null ||
                partitionedQueryExecutionInfo.QueryRanges == null ||
                partitionedQueryExecutionInfo.QueryInfo == null ||
                partitionedQueryExecutionInfo.QueryRanges.Any(range => range.Min == null || range.Max == null))
            {
                throw new InvalidOperationException($"{nameof(partitionedQueryExecutionInfo)} has invalid properties");
            }

            return(partitionedQueryExecutionInfo);
        }
        public TryCatch <PartitionedQueryExecutionInfo> TryGetPartitionedQueryExecutionInfo(
            SqlQuerySpec querySpec,
            PartitionKeyDefinition partitionKeyDefinition,
            bool requireFormattableOrderByQuery,
            bool isContinuationExpected,
            bool allowNonValueAggregateQuery,
            bool hasLogicalPartitionKey,
            bool allowDCount)
        {
            TryCatch <PartitionedQueryExecutionInfoInternal> tryGetInternalQueryInfo = this.TryGetPartitionedQueryExecutionInfoInternal(
                querySpec: querySpec,
                partitionKeyDefinition: partitionKeyDefinition,
                requireFormattableOrderByQuery: requireFormattableOrderByQuery,
                isContinuationExpected: isContinuationExpected,
                allowNonValueAggregateQuery: allowNonValueAggregateQuery,
                hasLogicalPartitionKey: hasLogicalPartitionKey,
                allowDCount: allowDCount);

            if (!tryGetInternalQueryInfo.Succeeded)
            {
                return(TryCatch <PartitionedQueryExecutionInfo> .FromException(tryGetInternalQueryInfo.Exception));
            }

            PartitionedQueryExecutionInfo queryInfo = this.ConvertPartitionedQueryExecutionInfo(tryGetInternalQueryInfo.Result, partitionKeyDefinition);

            return(TryCatch <PartitionedQueryExecutionInfo> .FromResult(queryInfo));
        }
Beispiel #11
0
        internal override async Task <IDocumentContainer> CreateDocumentContainerAsync(
            int numItems,
            FlakyDocumentContainer.FailureConfigs failureConfigs = default)
        {
            Documents.PartitionKeyDefinition partitionKeyDefinition = new Documents.PartitionKeyDefinition()
            {
                Paths = new System.Collections.ObjectModel.Collection <string>()
                {
                    "/pk"
                },
                Kind    = Documents.PartitionKind.Hash,
                Version = Documents.PartitionKeyDefinitionVersion.V2,
            };

            IMonadicDocumentContainer monadicDocumentContainer = new InMemoryContainer(partitionKeyDefinition);

            if (failureConfigs != null)
            {
                monadicDocumentContainer = new FlakyDocumentContainer(monadicDocumentContainer, failureConfigs);
            }

            DocumentContainer documentContainer = new DocumentContainer(monadicDocumentContainer);

            for (int i = 0; i < 3; i++)
            {
                IReadOnlyList <FeedRangeInternal> ranges = await documentContainer.GetFeedRangesAsync(
                    trace : NoOpTrace.Singleton,
                    cancellationToken : default);
Beispiel #12
0
        public static async Task <PartitionedQueryExecutionInfo> GetQueryPlanWithServiceInteropAsync(
            CosmosQueryClient queryClient,
            SqlQuerySpec sqlQuerySpec,
            Documents.ResourceType resourceType,
            PartitionKeyDefinition partitionKeyDefinition,
            bool hasLogicalPartitionKey,
            bool useSystemPrefix,
            ITrace trace,
            CancellationToken cancellationToken = default)
        {
            if (queryClient == null)
            {
                throw new ArgumentNullException(nameof(queryClient));
            }

            if (sqlQuerySpec == null)
            {
                throw new ArgumentNullException(nameof(sqlQuerySpec));
            }

            if (partitionKeyDefinition == null)
            {
                throw new ArgumentNullException(nameof(partitionKeyDefinition));
            }

            cancellationToken.ThrowIfCancellationRequested();

            using (ITrace serviceInteropTrace = trace.StartChild("Service Interop Query Plan", TraceComponent.Query, TraceLevel.Info))
            {
                QueryPlanHandler queryPlanHandler = new QueryPlanHandler(queryClient);

                TryCatch <PartitionedQueryExecutionInfo> tryGetQueryPlan = await queryPlanHandler.TryGetQueryPlanAsync(
                    sqlQuerySpec,
                    resourceType,
                    partitionKeyDefinition,
                    QueryPlanRetriever.SupportedQueryFeatures,
                    hasLogicalPartitionKey,
                    useSystemPrefix,
                    cancellationToken);

                if (!tryGetQueryPlan.Succeeded)
                {
                    Exception originalException = ExceptionWithStackTraceException.UnWrapMonadExcepion(tryGetQueryPlan.Exception, serviceInteropTrace);
                    if (originalException is CosmosException)
                    {
                        throw originalException;
                    }

                    throw CosmosExceptionFactory.CreateBadRequestException(
                              message: originalException.Message,
                              headers: new Headers(),
                              stackTrace: tryGetQueryPlan.Exception.StackTrace,
                              innerException: originalException,
                              trace: trace);
                }

                return(tryGetQueryPlan.Result);
            }
        }
Beispiel #13
0
 public abstract Task <TryCatch <PartitionedQueryExecutionInfo> > TryGetPartitionedQueryExecutionInfoAsync(
     SqlQuerySpec sqlQuerySpec,
     Documents.PartitionKeyDefinition partitionKeyDefinition,
     bool requireFormattableOrderByQuery,
     bool isContinuationExpected,
     bool allowNonValueAggregateQuery,
     bool hasLogicalPartitionKey,
     CancellationToken cancellationToken);
Beispiel #14
0
 public override Task <List <Documents.Routing.Range <string> > > GetEffectiveRangesAsync(
     IRoutingMapProvider routingMapProvider,
     string containerRid,
     Documents.PartitionKeyDefinition partitionKeyDefinition) => Task.FromResult(
     new List <Documents.Routing.Range <string> >
 {
     Documents.Routing.Range <string> .GetPointRange(
         this.PartitionKey.InternalKey.GetEffectivePartitionKeyString(partitionKeyDefinition))
 });
 public override async Task<IEnumerable<string>> GetPartitionKeyRangesAsync(
     IRoutingMapProvider routingMapProvider,
     string containerRid,
     Documents.PartitionKeyDefinition partitionKeyDefinition,
     CancellationToken cancellationToken)
 {
     string effectivePartitionKeyString = this.PartitionKey.InternalKey.GetEffectivePartitionKeyString(partitionKeyDefinition);
     Documents.PartitionKeyRange range = await routingMapProvider.TryGetRangeByEffectivePartitionKeyAsync(containerRid, effectivePartitionKeyString);
     return new List<string>() { range.Id };
 }
Beispiel #16
0
        internal override async Task <IEnumerable <string> > GetPartitionKeyRangesAsync(
            IRoutingMapProvider routingMapProvider,
            string containerRid,
            Documents.PartitionKeyDefinition partitionKeyDefinition,
            CancellationToken cancellationToken)
        {
            IReadOnlyList <Documents.PartitionKeyRange> partitionKeyRanges = await routingMapProvider.TryGetOverlappingRangesAsync(containerRid, this.Range, forceRefresh : false);

            return(partitionKeyRanges.Select(partitionKeyRange => partitionKeyRange.Id));
        }
 internal override Task <List <Documents.Routing.Range <string> > > GetEffectiveRangesAsync(
     IRoutingMapProvider routingMapProvider,
     string containerRid,
     Documents.PartitionKeyDefinition partitionKeyDefinition,
     ITrace trace)
 {
     return(Task.FromResult(new List <Documents.Routing.Range <string> >()
     {
         this.Range
     }));
 }
        public override Task <IEnumerable <string> > GetPartitionKeyRangesAsync(
            IRoutingMapProvider routingMapProvider,
            string containerRid,
            Documents.PartitionKeyDefinition partitionKeyDefinition,
            CancellationToken cancellationToken)
        {
            IEnumerable <string> partitionKeyRanges = new List <string>()
            {
                this.PartitionKeyRangeId
            };

            return(Task.FromResult(partitionKeyRanges));
        }
Beispiel #19
0
        public static async Task <PartitionedQueryExecutionInfo> GetQueryPlanWithServiceInteropAsync(
            CosmosQueryClient queryClient,
            SqlQuerySpec sqlQuerySpec,
            PartitionKeyDefinition partitionKeyDefinition,
            bool hasLogicalPartitionKey,
            ITrace trace,
            CancellationToken cancellationToken = default)
        {
            if (queryClient == null)
            {
                throw new ArgumentNullException(nameof(queryClient));
            }

            if (sqlQuerySpec == null)
            {
                throw new ArgumentNullException(nameof(sqlQuerySpec));
            }

            if (partitionKeyDefinition == null)
            {
                throw new ArgumentNullException(nameof(partitionKeyDefinition));
            }

            cancellationToken.ThrowIfCancellationRequested();

            using (ITrace serviceInteropTrace = trace.StartChild("Service Interop Query Plan", TraceComponent.Query, TraceLevel.Info))
            {
                QueryPlanHandler queryPlanHandler = new QueryPlanHandler(queryClient);

                TryCatch <PartitionedQueryExecutionInfo> tryGetQueryPlan = await queryPlanHandler.TryGetQueryPlanAsync(
                    sqlQuerySpec,
                    partitionKeyDefinition,
                    QueryPlanRetriever.SupportedQueryFeatures,
                    hasLogicalPartitionKey,
                    cancellationToken);

                if (!tryGetQueryPlan.Succeeded)
                {
                    if (tryGetQueryPlan.Exception is CosmosException)
                    {
                        throw tryGetQueryPlan.Exception;
                    }

                    throw CosmosExceptionFactory.CreateBadRequestException(
                              message: tryGetQueryPlan.Exception.ToString(),
                              stackTrace: tryGetQueryPlan.Exception.StackTrace);
                }

                return(tryGetQueryPlan.Result);
            }
        }
Beispiel #20
0
        public async Task FeedRangePK_GetEffectiveRangesAsync()
        {
            Documents.PartitionKeyDefinition partitionKeyDefinition = new Documents.PartitionKeyDefinition();
            partitionKeyDefinition.Paths.Add("/id");
            PartitionKey          partitionKey          = new PartitionKey("test");
            FeedRangePartitionKey feedRangePartitionKey = new FeedRangePartitionKey(partitionKey);

            Documents.Routing.Range <string> range = Documents.Routing.Range <string> .GetPointRange(partitionKey.InternalKey.GetEffectivePartitionKeyString(partitionKeyDefinition));

            List <Documents.Routing.Range <string> > ranges = await feedRangePartitionKey.GetEffectiveRangesAsync(Mock.Of <IRoutingMapProvider>(), null, partitionKeyDefinition);

            Assert.AreEqual(1, ranges.Count);
            Assert.AreEqual(range, ranges[0]);
        }
Beispiel #21
0
        public override async Task <List <Documents.Routing.Range <string> > > GetEffectiveRangesAsync(
            IRoutingMapProvider routingMapProvider,
            string containerRid,
            Documents.PartitionKeyDefinition partitionKeyDefinition)
        {
            Documents.PartitionKeyRange pkRange = await routingMapProvider.TryGetPartitionKeyRangeByIdAsync(containerRid, this.PartitionKeyRangeId);

            if (pkRange == null)
            {
                throw new InvalidOperationException();
            }

            return(new List <Documents.Routing.Range <string> > {
                pkRange.ToRange()
            });
        }
        public static Task <PartitionedQueryExecutionInfo> GetQueryPlanWithServiceInteropAsync(
            CosmosQueryClient queryClient,
            SqlQuerySpec sqlQuerySpec,
            PartitionKeyDefinition partitionKeyDefinition,
            bool hasLogicalPartitionKey,
            CancellationToken cancellationToken)
        {
            QueryPlanHandler queryPlanHandler = new QueryPlanHandler(queryClient);

            return(queryPlanHandler.GetQueryPlanAsync(
                       sqlQuerySpec,
                       partitionKeyDefinition,
                       SupportedQueryFeatures,
                       hasLogicalPartitionKey,
                       cancellationToken));
        }
        private Task <TryCatch <PartitionedQueryExecutionInfo> > TryGetQueryInfoAsync(
            SqlQuerySpec sqlQuerySpec,
            PartitionKeyDefinition partitionKeyDefinition,
            bool hasLogicalPartitionKey,
            CancellationToken cancellationToken = default)
        {
            cancellationToken.ThrowIfCancellationRequested();

            return(this.queryClient.TryGetPartitionedQueryExecutionInfoAsync(
                       sqlQuerySpec: sqlQuerySpec,
                       partitionKeyDefinition: partitionKeyDefinition,
                       requireFormattableOrderByQuery: true,
                       isContinuationExpected: false,
                       allowNonValueAggregateQuery: true,
                       hasLogicalPartitionKey: hasLogicalPartitionKey,
                       cancellationToken: cancellationToken));
        }
Beispiel #24
0
        public async Task <PartitionedQueryExecutionInfo> GetQueryPlanAsync(
            SqlQuerySpec sqlQuerySpec,
            PartitionKeyDefinition partitionKeyDefinition,
            QueryFeatures supportedQueryFeatures,
            bool hasLogicalPartitionKey,
            CancellationToken cancellationToken)
        {
            cancellationToken.ThrowIfCancellationRequested();

            if (sqlQuerySpec == null)
            {
                throw new ArgumentNullException($"{nameof(sqlQuerySpec)}");
            }

            if (partitionKeyDefinition == null)
            {
                throw new ArgumentNullException($"{nameof(partitionKeyDefinition)}");
            }

            PartitionedQueryExecutionInfo partitionedQueryExecutionInfo = await this.queryClient
                                                                          .GetPartitionedQueryExecutionInfoAsync(
                sqlQuerySpec : sqlQuerySpec,
                partitionKeyDefinition : partitionKeyDefinition,
                requireFormattableOrderByQuery : true,
                isContinuationExpected : false,
                allowNonValueAggregateQuery : true,
                hasLogicalPartitionKey : hasLogicalPartitionKey,
                cancellationToken : cancellationToken);

            if (partitionedQueryExecutionInfo == null ||
                partitionedQueryExecutionInfo.QueryRanges == null ||
                partitionedQueryExecutionInfo.QueryInfo == null ||
                partitionedQueryExecutionInfo.QueryRanges.Any(range => range.Min == null || range.Max == null))
            {
                throw new InvalidOperationException($"{nameof(partitionedQueryExecutionInfo)} has invalid properties");
            }

            QueryInfo queryInfo = partitionedQueryExecutionInfo.QueryInfo;

            QueryPlanHandler.QueryPlanExceptionFactory.ThrowIfNotSupported(
                queryInfo,
                supportedQueryFeatures);

            return(partitionedQueryExecutionInfo);
        }
Beispiel #25
0
        public async Task <TryCatch <PartitionedQueryExecutionInfo> > TryGetQueryPlanAsync(
            SqlQuerySpec sqlQuerySpec,
            Documents.ResourceType resourceType,
            PartitionKeyDefinition partitionKeyDefinition,
            QueryFeatures supportedQueryFeatures,
            bool hasLogicalPartitionKey,
            bool useSystemPrefix,
            CancellationToken cancellationToken)
        {
            cancellationToken.ThrowIfCancellationRequested();

            if (sqlQuerySpec == null)
            {
                throw new ArgumentNullException($"{nameof(sqlQuerySpec)}");
            }

            if (partitionKeyDefinition == null)
            {
                throw new ArgumentNullException($"{nameof(partitionKeyDefinition)}");
            }

            TryCatch <PartitionedQueryExecutionInfo> tryGetQueryInfo = await this.TryGetQueryInfoAsync(
                sqlQuerySpec,
                resourceType,
                partitionKeyDefinition,
                hasLogicalPartitionKey,
                useSystemPrefix,
                cancellationToken);

            if (!tryGetQueryInfo.Succeeded)
            {
                return(tryGetQueryInfo);
            }

            if (QueryPlanExceptionFactory.TryGetUnsupportedException(
                    tryGetQueryInfo.Result.QueryInfo,
                    supportedQueryFeatures,
                    out Exception queryPlanHandlerException))
            {
                return(TryCatch <PartitionedQueryExecutionInfo> .FromException(queryPlanHandlerException));
            }

            return(tryGetQueryInfo);
        }
        public PartitionedQueryExecutionInfo GetPartitionedQueryExecutionInfo(
            Func <string, Exception> createBadRequestException,
            SqlQuerySpec querySpec,
            PartitionKeyDefinition partitionKeyDefinition,
            bool requireFormattableOrderByQuery,
            bool isContinuationExpected,
            bool allowNonValueAggregateQuery,
            bool hasLogicalPartitionKey)
        {
            PartitionedQueryExecutionInfoInternal queryInfoInternal = this.GetPartitionedQueryExecutionInfoInternal(
                createBadRequestException,
                querySpec,
                partitionKeyDefinition,
                requireFormattableOrderByQuery,
                isContinuationExpected,
                allowNonValueAggregateQuery,
                hasLogicalPartitionKey);

            return(this.ConvertPartitionedQueryExecutionInfo(queryInfoInternal, partitionKeyDefinition));
        }
Beispiel #27
0
        public static async Task <PartitionedQueryExecutionInfo> GetQueryPlanWithServiceInteropAsync(
            CosmosQueryClient queryClient,
            SqlQuerySpec sqlQuerySpec,
            PartitionKeyDefinition partitionKeyDefinition,
            bool hasLogicalPartitionKey,
            CancellationToken cancellationToken = default(CancellationToken))
        {
            if (queryClient == null)
            {
                throw new ArgumentNullException(nameof(queryClient));
            }

            if (sqlQuerySpec == null)
            {
                throw new ArgumentNullException(nameof(sqlQuerySpec));
            }

            if (partitionKeyDefinition == null)
            {
                throw new ArgumentNullException(nameof(partitionKeyDefinition));
            }

            cancellationToken.ThrowIfCancellationRequested();
            QueryPlanHandler queryPlanHandler = new QueryPlanHandler(queryClient);

            TryCatch <PartitionedQueryExecutionInfo> tryGetQueryPlan = await queryPlanHandler.TryGetQueryPlanAsync(
                sqlQuerySpec,
                partitionKeyDefinition,
                QueryPlanRetriever.SupportedQueryFeatures,
                hasLogicalPartitionKey,
                cancellationToken);

            if (!tryGetQueryPlan.Succeeded)
            {
                throw new CosmosException(
                          System.Net.HttpStatusCode.BadRequest,
                          tryGetQueryPlan.Exception.Message);
            }

            return(tryGetQueryPlan.Result);
        }
        internal override async Task <List <Documents.Routing.Range <string> > > GetEffectiveRangesAsync(
            IRoutingMapProvider routingMapProvider,
            string containerRid,
            Documents.PartitionKeyDefinition partitionKeyDefinition,
            ITrace trace)
        {
            Documents.PartitionKeyRange pkRange = await routingMapProvider.TryGetPartitionKeyRangeByIdAsync(
                collectionResourceId : containerRid,
                partitionKeyRangeId : this.PartitionKeyRangeId,
                trace : trace,
                forceRefresh : false);

            if (pkRange == null)
            {
                // Try with a refresh
                pkRange = await routingMapProvider.TryGetPartitionKeyRangeByIdAsync(
                    collectionResourceId : containerRid,
                    partitionKeyRangeId : this.PartitionKeyRangeId,
                    trace : trace,
                    forceRefresh : true);
            }

            if (pkRange == null)
            {
                throw CosmosExceptionFactory.Create(
                          statusCode: HttpStatusCode.Gone,
                          message: $"The PartitionKeyRangeId: \"{this.PartitionKeyRangeId}\" is not valid for the current container {containerRid} .",
                          stackTrace: string.Empty,
                          headers: new Headers()
                {
                    SubStatusCode = SubStatusCodes.PartitionKeyRangeGone,
                },
                          error: null,
                          innerException: null,
                          trace: NoOpTrace.Singleton);
            }

            return(new List <Documents.Routing.Range <string> > {
                pkRange.ToRange()
            });
        }
        public static Task <PartitionedQueryExecutionInfo> GetPartitionedQueryExecutionInfoAsync(
            CosmosQueryClient queryClient,
            SqlQuerySpec sqlQuerySpec,
            Documents.PartitionKeyDefinition partitionKeyDefinition,
            bool requireFormattableOrderByQuery,
            bool isContinuationExpected,
            bool allowNonValueAggregateQuery,
            bool hasLogicalPartitionKey,
            CancellationToken cancellationToken)
        {
            // $ISSUE-felixfan-2016-07-13: We should probably get PartitionedQueryExecutionInfo from Gateway in GatewayMode

            return(queryClient.GetPartitionedQueryExecutionInfoAsync(
                       sqlQuerySpec,
                       partitionKeyDefinition,
                       requireFormattableOrderByQuery,
                       isContinuationExpected,
                       allowNonValueAggregateQuery,
                       hasLogicalPartitionKey,
                       cancellationToken));
        }
Beispiel #30
0
        /// <summary>
        /// Used in the compute gateway to support legacy gateways query execution pattern.
        /// </summary>
        public async Task <TryCatch <(PartitionedQueryExecutionInfo queryPlan, bool supported)> > TryGetQueryInfoAndIfSupportedAsync(
            QueryFeatures supportedQueryFeatures,
            SqlQuerySpec sqlQuerySpec,
            Documents.ResourceType resourceType,
            PartitionKeyDefinition partitionKeyDefinition,
            bool hasLogicalPartitionKey,
            bool useSystemPrefix,
            CancellationToken cancellationToken = default)
        {
            if (sqlQuerySpec == null)
            {
                throw new ArgumentNullException(nameof(sqlQuerySpec));
            }

            if (partitionKeyDefinition == null)
            {
                throw new ArgumentNullException(nameof(partitionKeyDefinition));
            }

            cancellationToken.ThrowIfCancellationRequested();

            TryCatch <PartitionedQueryExecutionInfo> tryGetQueryInfo = await this.TryGetQueryInfoAsync(
                sqlQuerySpec,
                resourceType,
                partitionKeyDefinition,
                hasLogicalPartitionKey,
                useSystemPrefix,
                cancellationToken);

            if (tryGetQueryInfo.Failed)
            {
                return(TryCatch <(PartitionedQueryExecutionInfo, bool)> .FromException(tryGetQueryInfo.Exception));
            }

            QueryFeatures neededQueryFeatures = QueryPlanSupportChecker.GetNeededQueryFeatures(
                tryGetQueryInfo.Result.QueryInfo,
                supportedQueryFeatures);

            return(TryCatch <(PartitionedQueryExecutionInfo, bool)> .FromResult((tryGetQueryInfo.Result, neededQueryFeatures == QueryFeatures.None)));
        }