public async Task Invoke(HttpContext context, IHostEnvironment webHostEnvironment) { // Using the Request-Id header, one can find the log for server-related exceptions context.Response.Headers.Add("Request-ID", context.TraceIdentifier); try { await _next(context); } catch (Exception e) { var exception = UnWrapException(e); var isKnownException = exception is KnownException; var statusCode = (int)(exception is RestException restExp ? restExp.StatusCode : HttpStatusCode.InternalServerError); RestExceptionPayload restExceptionPayload = new RestExceptionPayload { // The details of all of the exceptions are returned only in dev mode. in any other modes like production, only the details of the known exceptions are returned. Message = isKnownException || webHostEnvironment.IsDevelopment() ? exception.Message : nameof(UnknownException), ExceptionType = isKnownException ? exception.GetType().FullName : typeof(UnknownException).FullName }; if (exception is ResourceValidationException validationException) { restExceptionPayload.Details = validationException.Details; } context.Response.StatusCode = statusCode; await context.Response.WriteAsJsonAsync(restExceptionPayload); } }
protected override async Task <HttpResponseMessage> SendAsync(HttpRequestMessage request, CancellationToken cancellationToken) { if (request.Headers.Authorization is null && RuntimeInformation.ProcessArchitecture != Architecture.Wasm) { var access_token = await _tokenProvider.GetAcccessToken(); if (access_token is not null) { request.Headers.Authorization = new AuthenticationHeaderValue("Bearer", access_token); } } var response = await base.SendAsync(request, cancellationToken); if (!response.IsSuccessStatusCode && response.Content.Headers.ContentType?.MediaType == "application/json") { if (response.Headers.TryGetValues("Request-ID", out IEnumerable <string>?values) && values is not null && values.Any()) { RestExceptionPayload restError = await response.Content.ReadFromJsonAsync(TodoTemplateJsonContext.Default.RestExceptionPayload); Type exceptionType = typeof(RestExceptionPayload).Assembly.GetType(restError.ExceptionType) ?? typeof(UnknownException); Exception exp = (Exception)Activator.CreateInstance(exceptionType, args: new object[] { restError.Message }); if (exp is ResourceValidationException resValidationException) { resValidationException.Details = restError.Details; } throw exp; } } response.EnsureSuccessStatusCode(); return(response); }