private Task ConsumeSpecificationInformation(CancellationToken cancellationToken, dynamic context, IEnumerable <MergeSpecificationRequest> items) { ConcurrentDictionary <string, FundingPeriod> fundingPeriods = ((MergeContext)context).FundingPeriods; foreach (MergeSpecificationRequest mergeSpecificationRequest in items) { SpecificationInformation requestSpecificationInformation = mergeSpecificationRequest.SpecificationInformation; _logger.Information($"Merging specification information {requestSpecificationInformation.Name} for provider id {mergeSpecificationRequest.ProviderId}"); ProviderWithResultsForSpecifications providerWithResultsForSpecifications = GetProviderWithResultsForSpecificationsForProviderId(mergeSpecificationRequest.ProviderId); SpecificationInformation specificationInformation = new SpecificationInformation { Id = requestSpecificationInformation.Id, Name = requestSpecificationInformation.Name, LastEditDate = requestSpecificationInformation.LastEditDate, FundingPeriodId = requestSpecificationInformation.FundingPeriodId, FundingPeriodEnd = fundingPeriods.TryGetValue(requestSpecificationInformation.FundingPeriodId, out FundingPeriod fundingPeriod) ? fundingPeriod.EndDate : (DateTimeOffset?)null }; providerWithResultsForSpecifications.MergeSpecificationInformation(specificationInformation); } return(Task.CompletedTask); }
public async Task MergeSpecificationInformationMergesCreatesNewMissingProviderWithResultsForSpecificationsForSpecificProviderIdsWhenSupplied() { string jobId = NewRandomString(); string providerId = NewRandomString(); SpecificationInformation specificationInformation = NewSpecificationInformation(); MergeSpecificationInformationRequest mergeRequest = NewMergeSpecificationInformationRequest(_ => _.WithSpecificationInformation(specificationInformation) .WithProviderIds(providerId)); DateTimeOffset expectedFundingPeriodEndDate = NewRandomDateTime(); GivenTheFundingPeriodEndDate(specificationInformation.FundingPeriodId, expectedFundingPeriodEndDate); Message message = NewMessage(_ => _.WithUserProperty(JobId, jobId) .WithUserProperty(ProviderId, providerId) .WithMessageBody(mergeRequest.AsJsonBytes())); await WhenTheSpecificationInformationIsMerged(message); ThenTheJobTrackingWasStarted(jobId); SpecificationInformation expectedSpecificationInformation = specificationInformation.DeepCopy(); expectedSpecificationInformation.FundingPeriodEnd = expectedFundingPeriodEndDate; AndTheProviderWithResultsForSpecificationsWasUpserted(_ => _.Id == providerId && HasEquivalentSpecificationInformation(_, expectedSpecificationInformation)); AndTheJobTrackingWasCompleted(jobId); }
private async Task MergeSpecificationInformationForProviderBatch(SpecificationInformation specificationInformation, IEnumerable <string> providerIds, ConcurrentDictionary <string, FundingPeriod> fundingPeriods) { LogInformation($"Merging specification information for specification {specificationInformation.Id} into summary for provider batch with length {providerIds.Count()}"); foreach (string providerId in providerIds) { LogInformation($"Merging specification information for specification {specificationInformation.Id} into summary for provider {providerId}"); ProviderWithResultsForSpecifications providerWithResultsForSpecifications = await GetProviderWithResultsByProviderId(providerId); providerWithResultsForSpecifications ??= new ProviderWithResultsForSpecifications { Provider = new ProviderInformation { Id = providerId } }; await EnsureFundingPeriodEndDateQueried(specificationInformation, fundingPeriods); providerWithResultsForSpecifications.MergeSpecificationInformation(specificationInformation); if (providerWithResultsForSpecifications.GetIsDirty()) { await _results.UpsertSpecificationWithProviderResults(providerWithResultsForSpecifications); } } LogInformation($"Completed merging specification information for specification {specificationInformation.Id} into summary for provider batch with length {providerIds.Count()}"); }
private async Task EnsureFundingPeriodEndDateQueried(SpecificationInformation specificationInformation, ConcurrentDictionary <string, FundingPeriod> fundingPeriods = null) { if (specificationInformation.FundingPeriodEnd.HasValue) { LogInformation($"Specification funding period end date for information for {specificationInformation.Id} already present."); } LogInformation($"Querying funding period end date for information for {specificationInformation.Id}"); specificationInformation.FundingPeriodEnd = await GetFundingPeriodEndDate(specificationInformation.FundingPeriodId, fundingPeriods); }
public async Task MergeSpecificationInformationMergesForSpecificProviderIdsWhenSupplied() { string providerOneId = NewRandomString(); string providerTwoId = NewRandomString(); string jobId = NewRandomString(); string newFundingStreamIdOne = NewRandomString(); string newFundingStreamIdTwo = NewRandomString(); SpecificationInformation specificationInformation = NewSpecificationInformation(_ => _.WithFundingStreamIds(newFundingStreamIdOne, newFundingStreamIdTwo)); MergeSpecificationInformationRequest mergeRequest = NewMergeSpecificationInformationRequest(_ => _.WithSpecificationInformation(specificationInformation) .WithProviderIds(providerOneId, providerTwoId)); SpecificationInformation informationWithoutFundingStreams = specificationInformation.DeepCopy(); informationWithoutFundingStreams.FundingStreamIds = null; ProviderWithResultsForSpecifications providerWithResultsForSpecificationsOne = NewProviderWithResultsForSpecifications(_ => _.WithSpecifications(informationWithoutFundingStreams)); ProviderWithResultsForSpecifications providerWithResultsForSpecificationsTwo = NewProviderWithResultsForSpecifications(_ => _.WithSpecifications(informationWithoutFundingStreams)); GivenTheProviderWithResultsForSpecificationsByProviderId(providerWithResultsForSpecificationsOne, providerOneId); GivenTheProviderWithResultsForSpecificationsByProviderId(providerWithResultsForSpecificationsTwo, providerTwoId); Message message = NewMessage(_ => _.WithUserProperty(JobId, jobId) .WithMessageBody(mergeRequest.AsJsonBytes())); await WhenTheSpecificationInformationIsMerged(message); ThenTheJobTrackingWasStarted(jobId); AndTheProviderWithResultsForSpecificationsWereUpserted(providerWithResultsForSpecificationsOne); AndTheProviderWithResultsForSpecificationsWereUpserted(providerWithResultsForSpecificationsTwo); specificationInformation.IsDirty = true; providerWithResultsForSpecificationsOne .Specifications .Should() .BeEquivalentTo(specificationInformation); providerWithResultsForSpecificationsTwo .Specifications .Should() .BeEquivalentTo(specificationInformation); AndTheJobTrackingWasCompleted(jobId); }
private async Task MergeSpecificationInformationForAllProviders(SpecificationInformation specificationInformation) { string specificationId = specificationInformation.Id; LogInformation($"Merging specification information for specification {specificationId} into summary for all providers with results currently tracking it"); ICosmosDbFeedIterator <ProviderWithResultsForSpecifications> providersWithResultsForSpecifications = GetProviderWithResultsBySpecificationId(specificationId); await EnsureFundingPeriodEndDateQueried(specificationInformation); MergeSpecificationInformationContext context = new MergeSpecificationInformationContext(providersWithResultsForSpecifications, specificationInformation); IProducerConsumer producerConsumer = _producerConsumerFactory.CreateProducerConsumer(ProduceProviderWithResultsForSpecifications, MergeSpecificationInformation, 200, 2, _logger); await producerConsumer.Run(context); }
private async Task MergeSpecificationInformation(CancellationToken cancellationToken, dynamic context, IEnumerable <ProviderWithResultsForSpecifications> items) { SpecificationInformation specificationInformation = ((MergeSpecificationInformationContext)context).SpecificationInformation; LogInformation($"Merging SpecificationInformation for next {items.Count()} ProviderWithResultsForSpecifications"); foreach (ProviderWithResultsForSpecifications providerWithResultsForSpecification in items) { providerWithResultsForSpecification.MergeSpecificationInformation(specificationInformation); LogInformation($"Merged specification information for {specificationInformation.Id} into ProviderWithResultsForSpecifications for provider {providerWithResultsForSpecification.Id}"); } LogInformation($"Upserting page with {items.Count()} merged ProviderWithResultsForSpecifications for specification {specificationInformation.Id}"); ProviderWithResultsForSpecifications[] dirtyItems = items.Where(_ => _.GetIsDirty()).ToArray(); await _resultsPolicy.ExecuteAsync(() => _results.UpsertSpecificationWithProviderResults(dirtyItems)); }
public MergeSpecificationRequest(SpecificationInformation specificationInformation, string providerId) { SpecificationInformation = specificationInformation; ProviderId = providerId; }
public MergeSpecificationInformationContext(ICosmosDbFeedIterator <ProviderWithResultsForSpecifications> feedIterator, SpecificationInformation specificationInformation) { FeedIterator = feedIterator; SpecificationInformation = specificationInformation; }
public MergeSpecificationInformationRequestBuilder WithSpecificationInformation(SpecificationInformation specificationInformation) { _specificationInformation = specificationInformation; return(this); }
private Message NewMessage(SpecificationInformation specificationInformation, params (string key, string value)[] properties)
private void AndTheProviderWithResultsForSpecificationsHaveTheEquivalentSpecificationInformation(SpecificationInformation specificationInformation, params ProviderWithResultsForSpecifications[] providerWithResultsForSpecifications) { foreach (ProviderWithResultsForSpecifications providerWithResultsForSpecification in providerWithResultsForSpecifications) { providerWithResultsForSpecification .Specifications .Should() .BeEquivalentTo(new [] { specificationInformation }, opt => opt.Excluding(_ => _.IsDirty)); } }
public async Task MergeSpecificationInformationMergesForAllProviderWhenProviderIdNotSupplied() { string jobId = NewRandomString(); string specificationId = NewRandomString(); SpecificationInformation specificationInformation = NewSpecificationInformation(_ => _.WithId(specificationId)); MergeSpecificationInformationRequest mergeRequest = NewMergeSpecificationInformationRequest(_ => _.WithSpecificationInformation(specificationInformation)); ProviderWithResultsForSpecifications providerOne = NewProviderWithResultsForSpecifications(); ProviderWithResultsForSpecifications providerTwo = NewProviderWithResultsForSpecifications(); ProviderWithResultsForSpecifications providerThree = NewProviderWithResultsForSpecifications(); ProviderWithResultsForSpecifications providerFour = NewProviderWithResultsForSpecifications(); ProviderWithResultsForSpecifications providerFive = NewProviderWithResultsForSpecifications(); ProviderWithResultsForSpecifications providerSix = NewProviderWithResultsForSpecifications(); ProviderWithResultsForSpecifications providerSeven = NewProviderWithResultsForSpecifications(); ProviderResult providerResultEight = NewProviderResult(); ProviderWithResultsForSpecifications providerEight = NewProviderWithResultsForSpecifications(providerInformation: new ProviderInformation { Id = providerResultEight.Provider.Id }); ProviderResult providerResultNine = NewProviderResult(); ProviderWithResultsForSpecifications providerNine = NewProviderWithResultsForSpecifications(providerInformation: new ProviderInformation { Id = providerResultNine.Provider.Id }); DateTimeOffset expectedFundingPeriodEndDate = NewRandomDateTime(); GivenTheFundingPeriodEndDate(specificationInformation.FundingPeriodId, expectedFundingPeriodEndDate); AndTheProviderWithResultsForSpecifications(specificationId, NewFeedIterator(AsArray(providerOne, providerTwo), AsArray(providerThree, providerFour), AsArray(providerFive, providerSix), AsArray(providerSeven, providerEight))); AndTheProviderResultsForSpecification(specificationId, new[] { providerResultEight, providerResultNine }); Message message = NewMessage(_ => _.WithUserProperty(JobId, jobId) .WithMessageBody(mergeRequest.AsJsonBytes())); await WhenTheSpecificationInformationIsMerged(message); ThenTheJobTrackingWasStarted(jobId); SpecificationInformation expectedSpecificationInformation = specificationInformation.DeepCopy(); expectedSpecificationInformation.FundingPeriodEnd = expectedFundingPeriodEndDate; AndTheProviderWithResultsForSpecificationsWereUpserted(providerOne, providerTwo); AndTheProviderWithResultsForSpecificationsWereUpserted(providerThree, providerFour); AndTheProviderWithResultsForSpecificationsWereUpserted(providerFive, providerSix); AndTheProviderWithResultsForSpecificationsWereUpserted(providerSeven, providerEight); //only upserts dirty records AndTheProviderWithResultsForSpecificationsWereNotUpserted(providerNine); expectedSpecificationInformation.IsDirty = true; AndTheProviderWithResultsForSpecificationsHaveTheEquivalentSpecificationInformation(expectedSpecificationInformation, providerOne, providerTwo, providerThree, providerFour, providerFive, providerSix, providerSeven); AndTheJobTrackingWasCompleted(jobId); }