public async Task <WebServiceMetricsResponse> RunMetrics(WebServiceMetricsRequest request) { var response = new WebServiceMetricsResponse { WebServiceMetricsRequestMeasured = request }; var metricsRunEntity = new MetricsRun() { RequestBody = request.RequestBody, RequestUrl = request.RequestUrl, NumberOfRequestsToSend = request.NumberOfRequestsToSend }; using (var repository = new MetricsRepository()) { metricsRunEntity = await repository.SaveMetricsRun(metricsRunEntity); } response.WebServiceMetricsRunId = metricsRunEntity.MetricRunId; var tasks = new List <Task>(); using (var semaphore = new SemaphoreSlim(10)) { for (int i = 0; i < request.NumberOfRequestsToSend; i++) { await semaphore.WaitAsync(); tasks.Add(MeasureRequest(semaphore, request, response)); } await Task.WhenAll(tasks); } return(response); }
private static async Task MeasureRequest(SemaphoreSlim semaphore, WebServiceMetricsRequest request, WebServiceMetricsResponse response) { try { var httpClient = new HttpClient(); var uri = new Uri(request.RequestUrl); var sw = new Stopwatch(); sw.Start(); var wsResponse = await httpClient.PostAsync(uri, new StringContent(request.RequestBody, Encoding.Unicode, "application/json")); sw.Stop(); var metricsResultEntity = new MetricsResult() { MetricsRunId = response.WebServiceMetricsRunId, TimeElapsedInMilliseconds = (int)sw.ElapsedMilliseconds, Result = wsResponse.StatusCode.ToString() }; //use separate repository each time since .NET/EF Core cannot multi-thread the same DbContext... using (var repository = new MetricsRepository()) { await repository.SaveMetricsResult(metricsResultEntity); } response.WebServiceMetricsResults.Add(new WebServiceMetricsResultDto { TimeElapsedInMilliseconds = metricsResultEntity.TimeElapsedInMilliseconds.ToString() }); } catch (Exception ex) { response.WebServiceMetricsResults.Add(new WebServiceMetricsResultDto() { ErrorMessage = ex.Message }); } finally { semaphore.Release(); } }