// log the request private static void LogRequest(HttpContext context, CorrelationVector cv, double ttfb, double duration) { DateTime dt = DateTime.UtcNow; Dictionary <string, object> log = new Dictionary <string, object> { { "Date", dt }, { "LogName", "Ngsa.RequestLog" }, { "StatusCode", context.Response.StatusCode }, { "TTFB", ttfb }, { "Duration", duration }, { "Verb", context.Request.Method }, { "Path", GetPathAndQuerystring(context.Request) }, { "Host", context.Request.Headers["Host"].ToString() }, { "ClientIP", GetClientIp(context) }, { "UserAgent", context.Request.Headers["User-Agent"].ToString() }, { "CVector", cv.Value }, { "CVectorBase", cv.GetBase() }, }; if (!string.IsNullOrWhiteSpace(CosmosName)) { log.Add("CosmosName", CosmosName); } if (!string.IsNullOrWhiteSpace(CosmosQueryId)) { log.Add("CosmosQueryId", CosmosQueryId); } if (CosmosRUs > 0) { log.Add("CosmosRUs", CosmosRUs); } if (!string.IsNullOrWhiteSpace(DataService)) { log.Add("DataService", DataService); } Interlocked.Increment(ref counter); // write the results to the console Console.WriteLine(JsonSerializer.Serialize(log)); }
/// <summary> /// Execute a single validation test /// </summary> /// <param name="client">http client</param> /// <param name="server">server URL</param> /// <param name="request">Request</param> /// <returns>PerfLog</returns> public async Task <PerfLog> ExecuteRequest(HttpClient client, string server, Request request) { if (request == null) { throw new ArgumentNullException(nameof(request)); } if (client == null) { throw new ArgumentNullException(nameof(client)); } PerfLog perfLog; ValidationResult valid; // send the request using (HttpRequestMessage req = new HttpRequestMessage(new HttpMethod(request.Verb), request.Path)) { DateTime dt = DateTime.UtcNow; // add the headers to the http request if (request.Headers != null && request.Headers.Count > 0) { foreach (string key in request.Headers.Keys) { req.Headers.Add(key, request.Headers[key]); } } // create correlation vector and add to headers CorrelationVector cv = new CorrelationVector(CorrelationVectorVersion.V2); req.Headers.Add(CorrelationVector.HeaderName, cv.Value); // add the body to the http request if (!string.IsNullOrWhiteSpace(request.Body)) { if (!string.IsNullOrWhiteSpace(request.ContentMediaType)) { req.Content = new StringContent(request.Body, Encoding.UTF8, request.ContentMediaType); } else { req.Content = new StringContent(request.Body); } } try { // process the response using HttpResponseMessage resp = await client.SendAsync(req).ConfigureAwait(false); string body = await resp.Content.ReadAsStringAsync().ConfigureAwait(false); double duration = DateTime.UtcNow.Subtract(dt).TotalMilliseconds; // validate the response valid = ResponseValidator.Validate(request, resp, body); // check the performance perfLog = CreatePerfLog(server, request, valid, duration, (long)resp.Content.Headers.ContentLength, (int)resp.StatusCode); // add correlation vector to perf log perfLog.CorrelationVector = cv.Value; perfLog.CorrelationVectorBase = cv.GetBase(); } catch (Exception ex) { double duration = Math.Round(DateTime.UtcNow.Subtract(dt).TotalMilliseconds, 0); valid = new ValidationResult { Failed = true }; valid.ValidationErrors.Add($"Exception: {ex.Message}"); perfLog = CreatePerfLog(server, request, valid, duration, 0, 500); } } // log the test LogToConsole(request, valid, perfLog); if (config.Prometheus) { // map category and mode to app values string mode = GetMode(perfLog, out string category); RequestDuration.WithLabels(perfLog.StatusCode.ToString(), category, mode, perfLog.Server, perfLog.Failed.ToString(), config.Zone, config.Region).Observe(perfLog.Duration); } return(perfLog); }