/// <summary> /// Bulk pin content hashes. /// </summary> private async Task <PinBulkResponse> PinBulkAsync(PinBulkRequest request, CancellationToken token) { LogRequestHandling(); DateTime startTime = DateTime.UtcNow; var cacheContext = new Context(new Guid(request.Header.TraceId), _logger); return(await RunFuncAndReportAsync( request.Header.SessionId, async session => { var pinList = new List <ContentHash>(); foreach (var hash in request.Hashes) { pinList.Add(hash.ContentHash.ToContentHash((HashType)hash.HashType)); } List <Task <Indexed <PinResult> > > pinResults = (await session.PinAsync( cacheContext, pinList, token)).ToList(); var response = new PinBulkResponse(); try { foreach (var pinResult in pinResults) { var result = await pinResult; var responseHeader = new ResponseHeader( startTime, result.Item.Succeeded, (int)result.Item.Code, result.Item.ErrorMessage, result.Item.Diagnostics); response.Header.Add(result.Index, responseHeader); } } catch (Exception) { pinResults.ForEach(task => task.FireAndForget(cacheContext)); throw; } return response; }, errorMessage => { var header = ResponseHeader.Failure(startTime, (int)PinResult.ResultCode.Error, errorMessage); var response = new PinBulkResponse(); int i = 0; foreach (var hash in request.Hashes) { response.Header.Add(i, header); i++; } return response; })); }
private Task <PinBulkResponse> PinBulkAsync(PinBulkRequest request, CancellationToken token) { return(RunFuncAsync( request.Header, async(context, session) => { var pinList = new List <ContentHash>(); foreach (var hash in request.Hashes) { pinList.Add(hash.ContentHash.ToContentHash((HashType)hash.HashType)); } List <Task <Indexed <PinResult> > > pinResults = (await session.PinAsync( context.OperationContext, pinList, context.Token)).ToList(); var response = new PinBulkResponse(); try { foreach (var pinResult in pinResults) { var result = await pinResult; var responseHeader = new ResponseHeader( context.StartTime, result.Item.Succeeded, (int)result.Item.Code, result.Item.ErrorMessage, result.Item.Diagnostics); response.Header.Add(result.Index, responseHeader); } } catch (Exception) { pinResults.ForEach(task => task.FireAndForget(context.OperationContext)); throw; } return response; }, (context, errorMessage) => { var header = ResponseHeader.Failure(context.StartTime, (int)PinResult.ResultCode.Error, errorMessage); var response = new PinBulkResponse(); int i = 0; foreach (var hash in request.Hashes) { response.Header.Add(i, header); i++; } return response; }, token)); }
private async Task <IEnumerable <Task <Indexed <PinResult> > > > PinBatchAsync(Context context, int baseIndex, IReadOnlyList <ContentHash> chunk) { StructResult <int> sessionResult = await _sessionState.GetIdAsync(); if (!sessionResult.Succeeded) { PinResult pinResult = new PinResult(sessionResult); return(chunk.Select((ContentHash h) => pinResult).AsIndexed().AsTasks()); } int sessionId = sessionResult.Data; var pinResults = new List <Indexed <PinResult> >(); var bulkPinRequest = new PinBulkRequest { Header = new RequestHeader(context.Id, sessionId) }; foreach (var contentHash in chunk) { bulkPinRequest.Hashes.Add( new ContentHashAndHashTypeData { HashType = (int)contentHash.HashType, ContentHash = contentHash.ToByteString() }); } DateTime startTime = DateTime.UtcNow; PinBulkResponse underlyingBulkPinResponse = await RunClientActionAndThrowIfFailedAsync( context, async() => await _client.PinBulkAsync(bulkPinRequest)); long ticksWaited = underlyingBulkPinResponse.Header.Values.First().ServerReceiptTimeUtcTicks - startTime.Ticks; _tracer.TrackClientWaitForServerTicks(ticksWaited); foreach (var response in underlyingBulkPinResponse.Header) { await ResetOnUnknownSessionAsync(context, response.Value, sessionId); pinResults.Add(UnpackPinResult(response.Value).WithIndex(response.Key + baseIndex)); } _tracer.LogPinResults(context, pinResults.Select(r => chunk[r.Index - baseIndex]).ToList(), pinResults.Select(r => r.Item).ToList()); return(pinResults.AsTasks()); }
private async Task <IEnumerable <Task <Indexed <PinResult> > > > PinBatchAsync(Context context, int baseIndex, IReadOnlyList <ContentHash> chunk) { // This operation is quite different from others because there is no single header response. // So instead of using a common functionality we have handle this case separately. var sessionContext = await CreateSessionContextAsync(context); if (!sessionContext) { PinResult pinResult = new PinResult(sessionContext); return(chunk.Select((ContentHash h) => pinResult).AsIndexed().AsTasks()); } int sessionId = sessionContext.Value.SessionId; var pinResults = new List <Indexed <PinResult> >(); var bulkPinRequest = new PinBulkRequest { Header = new RequestHeader(context.TraceId, sessionId) }; foreach (var contentHash in chunk) { bulkPinRequest.Hashes.Add( new ContentHashAndHashTypeData { HashType = (int)contentHash.HashType, ContentHash = contentHash.ToByteString() }); } PinBulkResponse underlyingBulkPinResponse = await SendGrpcRequestAndThrowIfFailedAsync( sessionContext.Value, async() => await Client.PinBulkAsync(bulkPinRequest), throwFailures : false); var info = underlyingBulkPinResponse.Info.Count == 0 ? null : underlyingBulkPinResponse.Info; foreach (var response in underlyingBulkPinResponse.Header) { await ResetOnUnknownSessionAsync(context, response.Value, sessionId); pinResults.Add(UnpackPinResult(response.Value, info?[response.Key]).WithIndex(response.Key + baseIndex)); } ServiceClientTracer.LogPinResults(context, pinResults.Select(r => chunk[r.Index - baseIndex]).ToList(), pinResults.Select(r => r.Item).ToList()); return(pinResults.AsTasks()); }