private async Task <Exception> ZipApiExceptionFromResponseAsync(HttpResponseMessage response) { ZipErrorResponse errors = null !; //If we fail to parse the error body that's unfortunate, but don't hide the original error. //TODO: should perhaps log or otherwise expose the deserialisation failure without hiding the //original exception. For now, just do our best to report the exception that really matters (original). string?content = null; if (response.Content != null) { content = await response.Content.ReadAsStringAsync().ConfigureAwait(false); } if (!String.IsNullOrEmpty(content)) { try { errors = System.Text.Json.JsonSerializer.Deserialize <ZipErrorResponse>(content, _SerializerOptions); errors.ResponseCode = Convert.ToInt32(response.StatusCode, System.Globalization.CultureInfo.InvariantCulture); } catch { } } if (errors == null) { errors = new ZipErrorResponse() { Message = response.ReasonPhrase, ResponseCode = Convert.ToInt32(response.StatusCode, System.Globalization.CultureInfo.InvariantCulture) }; } throw new ZipApiException(errors); }
private static string ErrorMessageFromZipErrors(ZipErrorResponse error) { //Often (not always) a '400' response has a pretty generic 'error.Message' value which isn't helpful (i.e 'The request is invalid'), //in this case include the 'error.ErrorCode' value which often provides a better hint about what is wrong ('AboveMaximumPreApprovalAmount'). if (error.ResponseCode == 400 && !String.IsNullOrEmpty(error.ErrorCode) && !String.IsNullOrEmpty(error.Message)) { return($"({error.ErrorCode}) {error.Message}"); } return(error?.Message ?? error?.Detail ?? error?.ValidationErrors?.FirstOrDefault().ErrorMessages?.FirstOrDefault() ?? error?.ErrorCode ?? error?.Title ?? ErrorMessage.UnknownApiError); }
/// <summary> /// Full constructor, recommended. /// </summary> /// <param name="error">A <see cref="ZipErrorResponse"/> containing full errors received from the Zip API.</param> /// <param name="inner">Another exception being wrapped by this one.</param> public ZipApiException(ZipErrorResponse error, Exception inner) : base(ErrorMessageFromZipErrors(error), inner) { Errors = error; }