/// <summary> /// intercepts the http request that was about to hit a downstream server and return a stub instead /// </summary> /// <param name="request"></param> /// <param name="cancellationToken"></param> /// <returns></returns> protected async override Task <HttpResponseMessage> SendAsync(HttpRequestMessage request, CancellationToken cancellationToken) { var session = ContextRepo.GetSession(); if (session == null) { throw new ApplicationException("No session found"); } var requestWrapper = new HttpRequestMessageWrapper(request); ContextRepo.OutgoingRequests[session].Add(requestWrapper); // there could be more than one stub for the same endpoint, perhaps returning different responses, we grab the first var match = ContextRepo.StubbedEndpoints[session].FirstOrDefault(c => c.IsMatch(requestWrapper)); if (match == null) { throw new ApplicationException($"No stubs found for [{requestWrapper.GetEndpoint()}], please make sure you called 'AppendHttpCallStub'"); } ContextRepo.StubbedEndpoints[session].Remove(match); if (match.Exception != null) { throw match.Exception; } return(match.Response); }
public void Log <TState>(LogLevel logLevel, EventId eventId, TState state, Exception exception, Func <TState, Exception, string> formatter) { var session = ContextRepo.GetSession(); var log = new LoggedEvent(logLevel, formatter(state, exception), source); if (session == null) { ContextRepo.UnsessionedLogs.Add(log); } else { ContextRepo.SessionLogs[session].Add(log); } }
internal async Task <RequestResponse> Summarize(HttpRequestMessage request, HttpResponseMessage response) { var result = new RequestResponse(); result.Metadata.DateTime = DateTime.Now; result.Metadata.Timezone = TimeZoneInfo.Local.ToString(); result.Metadata.RecordedFrom = $"{ContextRepo.GetAppNameAndVersion()} ({ContextRepo.GetUrl()})"; result.Metadata.User = $"{Environment.UserDomainName}\\{Environment.UserName}"; result.Metadata.LocalMachine = Environment.MachineName; result.Metadata.ToolUrl = Constants.Website; result.Metadata.ToolNameAndVersion = _toolNameAndVersion; result.Request.Method = request.Method; result.Request.Url = request.RequestUri.ToString(); if (request.Content != null) { result.Request.Body = await request.Content.ReadAsStringAsync(); } result.Request.Headers.ApppendHeaders(FormatHeaders(request.Headers)); if (request.Content?.Headers != null) { result.Request.Headers.ApppendHeaders(FormatHeaders(request.Content.Headers)); } result.Response.Status = response.StatusCode; result.Response.HttpVersion = response.Version; if (response.Content != null) { result.Response.Body = await response.Content.ReadAsStringAsync(); } result.Response.Headers.ApppendHeaders(FormatHeaders(response.Headers)); if (response.Content?.Headers != null) { result.Response.Headers.ApppendHeaders(FormatHeaders(response.Content.Headers)); } return(result); // new feature in C#7 (https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/classes-and-structs/local-functions) Dictionary <string, string> FormatHeaders(HttpHeaders headers) { var dic = headers.ToList().ToDictionary(c => c.Key, c => c.Value.SeparatedByComa()); return(dic); } }