public async Task <ReindexJobWrapper> CreateReindexJobAsync(ReindexJobRecord jobRecord, CancellationToken cancellationToken) { EnsureArg.IsNotNull(jobRecord, nameof(jobRecord)); var cosmosReindexJob = new CosmosReindexJobRecordWrapper(jobRecord); try { var result = await _containerScope.Value.CreateItemAsync( cosmosReindexJob, new PartitionKey(CosmosDbReindexConstants.ReindexJobPartitionKey), cancellationToken : cancellationToken); return(new ReindexJobWrapper(jobRecord, WeakETag.FromVersionId(result.Resource.ETag))); } catch (CosmosException dce) { if (dce.IsRequestRateExceeded()) { throw; } _logger.LogError(dce, "Failed to create a reindex job."); throw; } }
public async Task <ReindexJobWrapper> CreateReindexJobAsync(ReindexJobRecord jobRecord, CancellationToken cancellationToken) { EnsureArg.IsNotNull(jobRecord, nameof(jobRecord)); var cosmosReindexJob = new CosmosReindexJobRecordWrapper(jobRecord); try { ResourceResponse <Document> result = await _documentClientScope.Value.CreateDocumentAsync( CollectionUri, cosmosReindexJob, new RequestOptions() { PartitionKey = new PartitionKey(CosmosDbReindexConstants.ReindexJobPartitionKey) }, disableAutomaticIdGeneration : true, cancellationToken : cancellationToken); return(new ReindexJobWrapper(jobRecord, WeakETag.FromVersionId(result.Resource.ETag))); } catch (DocumentClientException dce) { if (dce.StatusCode == HttpStatusCode.TooManyRequests) { throw new RequestRateExceededException(dce.RetryAfter); } _logger.LogError(dce, "Failed to create a reindex job."); throw; } }
public async Task <ReindexJobWrapper> UpdateReindexJobAsync(ReindexJobRecord jobRecord, WeakETag eTag, CancellationToken cancellationToken) { EnsureArg.IsNotNull(jobRecord, nameof(jobRecord)); var cosmosReindexJob = new CosmosReindexJobRecordWrapper(jobRecord); var requestOptions = new RequestOptions() { PartitionKey = new PartitionKey(CosmosDbReindexConstants.ReindexJobPartitionKey), }; // Create access condition so that record is replaced only if eTag matches. if (eTag != null) { requestOptions.AccessCondition = new AccessCondition() { Type = AccessConditionType.IfMatch, Condition = eTag.VersionId, }; } try { ResourceResponse <Document> replaceResult = await _retryExceptionPolicyFactory.CreateRetryPolicy().ExecuteAsync( () => _documentClientScope.Value.ReplaceDocumentAsync( UriFactory.CreateDocumentUri(DatabaseId, CollectionId, jobRecord.Id), cosmosReindexJob, requestOptions, cancellationToken)); var latestETag = replaceResult.Resource.ETag; return(new ReindexJobWrapper(jobRecord, WeakETag.FromVersionId(latestETag))); } catch (DocumentClientException dce) { if (dce.StatusCode == HttpStatusCode.TooManyRequests) { throw new RequestRateExceededException(dce.RetryAfter); } else if (dce.StatusCode == HttpStatusCode.PreconditionFailed) { throw new JobConflictException(); } else if (dce.StatusCode == HttpStatusCode.NotFound) { throw new JobNotFoundException(string.Format(Core.Resources.JobNotFound, jobRecord.Id)); } _logger.LogError(dce, "Failed to update a reindex job."); throw; } }
public async Task <ReindexJobWrapper> UpdateReindexJobAsync(ReindexJobRecord jobRecord, WeakETag eTag, CancellationToken cancellationToken) { EnsureArg.IsNotNull(jobRecord, nameof(jobRecord)); var cosmosReindexJob = new CosmosReindexJobRecordWrapper(jobRecord); var requestOptions = new ItemRequestOptions(); // Create access condition so that record is replaced only if eTag matches. if (eTag != null) { requestOptions.IfMatchEtag = eTag.VersionId; } try { var replaceResult = await _retryExceptionPolicyFactory.CreateRetryPolicy().ExecuteAsync( () => _containerScope.Value.ReplaceItemAsync( cosmosReindexJob, jobRecord.Id, new PartitionKey(CosmosDbReindexConstants.ReindexJobPartitionKey), requestOptions, cancellationToken)); var latestETag = replaceResult.Resource.ETag; return(new ReindexJobWrapper(jobRecord, WeakETag.FromVersionId(latestETag))); } catch (CosmosException dce) { if (dce.IsRequestRateExceeded()) { throw; } else if (dce.StatusCode == HttpStatusCode.PreconditionFailed) { throw new JobConflictException(); } else if (dce.StatusCode == HttpStatusCode.NotFound) { throw new JobNotFoundException(string.Format(Core.Resources.JobNotFound, jobRecord.Id)); } _logger.LogError(dce, "Failed to update a reindex job."); throw; } }
public async Task <IReadOnlyCollection <ReindexJobWrapper> > AcquireReindexJobsAsync(ushort maximumNumberOfConcurrentJobsAllowed, TimeSpan jobHeartbeatTimeoutThreshold, CancellationToken cancellationToken) { // TODO: Shell for testing IDocumentQuery <int> query = _documentClientScope.Value.CreateDocumentQuery <int>( CollectionUri, new SqlQuerySpec(CheckActiveJobsByStatusQuery), new FeedOptions { PartitionKey = new PartitionKey(CosmosDbReindexConstants.ReindexJobPartitionKey) }) .AsDocumentQuery(); FeedResponse <CosmosReindexJobRecordWrapper> result = await query.ExecuteNextAsync <CosmosReindexJobRecordWrapper>(); var jobList = new List <ReindexJobWrapper>(); CosmosReindexJobRecordWrapper cosmosJob = result.FirstOrDefault(); if (cosmosJob != null) { jobList.Add(new ReindexJobWrapper(cosmosJob.JobRecord, WeakETag.FromVersionId(cosmosJob.ETag))); } return(jobList); }
public async Task <IReadOnlyCollection <ReindexJobWrapper> > AcquireReindexJobsAsync(ushort maximumNumberOfConcurrentJobsAllowed, TimeSpan jobHeartbeatTimeoutThreshold, CancellationToken cancellationToken) { // TODO: Shell for testing var query = _queryFactory.Create <CosmosReindexJobRecordWrapper>( _containerScope.Value, new CosmosQueryContext( new QueryDefinition(CheckActiveJobsByStatusQuery), new QueryRequestOptions { PartitionKey = new PartitionKey(CosmosDbReindexConstants.ReindexJobPartitionKey) })); FeedResponse <CosmosReindexJobRecordWrapper> result = await query.ExecuteNextAsync(); var jobList = new List <ReindexJobWrapper>(); CosmosReindexJobRecordWrapper cosmosJob = result.FirstOrDefault(); if (cosmosJob != null) { jobList.Add(new ReindexJobWrapper(cosmosJob.JobRecord, WeakETag.FromVersionId(cosmosJob.ETag))); } return(jobList); }