ResponseEntityExceptionHandler возвращает пустое тело ответа для 401 исключения - PullRequest
0 голосов
/ 28 февраля 2019

Я пытаюсь реализовать вызов Rest на сервер аутентификации, используя RestTemplate, и регистрировать ответ в случае, если сервер возвращает исключение.Для этого я использовал ResponseEntityExceptionHandler для обработки HttpClientErrorException и HttpServerErrorException.

public Response sendRequest(Request requestBody, String url, HttpMethod httpMethod, Response responseBody) {
    RestTemplate restTemplate = new RestTemplate();
    HttpEntity<MultiValueMap<String, String>> request = new HttpEntity<>(requestBody.getBody(),
            this.securityHeaders);
    ResponseEntity<? extends Response> response = restTemplate.exchange(url, httpMethod, request,
            responseBody.getClass());
    return response.getBody();
}

В настоящее время мой ResponseEntityExceptionHandler имеет следующий вид

@ControllerAdvice
public class RestResponseExceptionHandler extends ResponseEntityExceptionHandler {

private static Logger log = LoggerFactory.getLogger(RestResponseExceptionHandler.class);
private HttpHeaders headers = new HttpHeaders();

@ExceptionHandler(value = { HttpClientErrorException.class, HttpServerErrorException.class })
protected ResponseEntity<Object> handleConflict(HttpStatusCodeException ex, WebRequest request) {
    ErrorMessage responseBody = new ErrorMessage();
    try {
        JSONObject bodyOfException = new JSONObject(ex.getResponseBodyAsString());
        log.warn("{}| {}", ex.getStatusCode(), bodyOfException);
        responseBody.setErrorAndDescription(bodyOfException.optString("error"),
                bodyOfException.optString("error_description"));
    } catch (JSONException e) {
        log.error("{}| Bad authentication response body | Response Body | {}", ex.getStatusCode(),
                ex.getResponseBodyAsString());
    }

    return handleExceptionInternal(ex, responseBody, headers, ex.getStatusCode(), request);
}

}

Однако,для исключений HttpStatus 401 я получаю пустое тело ответа.

Пример журналов:

400| {"error_description":"Bad client credentials","error":"invalid_client"}

401| Bad authentication response body | Response Body | 

Кто-нибудь знает, как я могу получить тело ответа для исключений 401?

Изменить: При использовании Почтальона для вызова сервера аутентификации я получаю ненулевое значение 401 responseBody:

{
 "error": "invalid_token",
 "error_description": "Token was not recognised"
}

Ответы [ 2 ]

0 голосов
/ 01 марта 2019

Я наконец смог зарегистрировать тело ответа для 401 Исключений.Я добавил зависимость

org.apache.httpcomponents: httpclient

и настроил фабрику запросов шаблонов отдыха

    restTemplate.setRequestFactory(new HttpComponentsClientHttpRequestFactory());

Очевидно, фабрика запросов по умолчанию SimpleClientHttpRequestFactoryне может прочитать тело ответа для 401 Http Status.

0 голосов
/ 28 февраля 2019

Почему вы считаете, что HttpStatusCodeException должен иметь тело ответа?Это не так.
Посмотрите на конструктор RestClientResponseException, его прямой суперкласс

 ...

 * @param responseBody the response body content (may be {@code null})
 * @param responseCharset the response body charset (may be {@code null})
 */
public RestClientResponseException(
        String message, 
        int statusCode,
        String statusText,
        @Nullable HttpHeaders responseHeaders, 
        @Nullable byte[] responseBody, 
        @Nullable Charset responseCharset) { ... }

. Вы должны ожидать этого случая и предоставить тело настраиваемого ответа.
Фактическое исключениеmessage - это хорошее значение для возврата как часть тела, которое может быть сложным объектом.

...