복붙노트

[SPRING] Spring RestTemplate - ResponseErrorHandler 무시

SPRING

Spring RestTemplate - ResponseErrorHandler 무시

RestTemplate을 통해 ReST 서비스를 호출하고 사용자 정의 오류 코드를 처리하기 위해 Spring 3.2에서 ResponseErrorHandler를 무시하려고합니다.

CustomResponseErrroHandler

public class MyResponseErrorHandler implements ResponseErrorHandler {

    @Override
    public boolean hasError(ClientHttpResponse response) throws IOException {
        boolean hasError = false;
        int rawStatusCode = response.getRawStatusCode();
        if (rawStatusCode != 200){
            hasError = true;
        }
        return hasError;
     }

    @Override
    public void handleError(ClientHttpResponse response) throws IOException {
        //String body = IOUtils.toString(response.getBody());
        throw new CustomServiceException(response.getRawStatusCode() , "custom Error");
   }
}

Spring 프레임 워크는 hasError 메소드를 호출하지만 handleError는 호출하지 않으므로 사용자 정의 예외를 throw 할 수 없습니다. Spring RestTemplate 소스 코드를 탐색 한 후 handleResponseError 메서드의 코드가 문제를 일으킨다는 것을 깨달았습니다. - response.getStatusCode 또는 response.getStatusText를 찾고 예외를 throw합니다 (Rest 서비스가 예외를 throw하면 statusCode / statusText가 null 임). 다음 라인에서 커스텀 구현 또는 디폴트 handleError 메소드를 결코 호출하지 않는다.

handleResponse 메소드의 Spring RestTemplate 소스 코드 :

private void handleResponseError(HttpMethod method, URI url, ClientHttpResponse response) throws IOException {
    if (logger.isWarnEnabled()) {
        try {
            logger.warn(method.name() + " request for \"" + url + "\" resulted in " +
response.getStatusCode() + " (" + response.getStatusText() + "); invoking error handler");
        }
        catch (IOException e) {
            // ignore
        }
    }
    getErrorHandler().handleError(response);
}

참고로, 서비스가 예외를 throw하는 동안 rawstatuscode는 읽을 수 있지만 응답의 상태 코드는 읽을 수 없습니다.

이 프레임 워크 코드를 무시하고 내 사용자 지정 처리기를 호출하는 방법? 미리 도움을 주셔서 감사합니다.

해결법

  1. ==============================

    1.다음 링크에는 Spring ResponseErrorHandler에 대한 예외 흐름에 대한 유용한 정보가 있습니다.

    다음 링크에는 Spring ResponseErrorHandler에 대한 예외 흐름에 대한 유용한 정보가 있습니다.

    여기에 코드를 추가하면 블로그가 다운되었을 때만 가능합니다.

    ErrorHandler의 코드 :

    public class MyResponseErrorHandler implements ResponseErrorHandler {
    
        private static final Log logger = LogFactory.getLog(MyResponseErrorHandler.class);
    
        @Override
        public void handleError(ClientHttpResponse clienthttpresponse) throws IOException {
    
            if (clienthttpresponse.getStatusCode() == HttpStatus.FORBIDDEN) {
                logger.debug(HttpStatus.FORBIDDEN + " response. Throwing authentication exception");
                throw new AuthenticationException();
            }
        }
    
        @Override
        public boolean hasError(ClientHttpResponse clienthttpresponse) throws IOException {
    
            if (clienthttpresponse.getStatusCode() != HttpStatus.OK) {
                logger.debug("Status code: " + clienthttpresponse.getStatusCode());
                logger.debug("Response" + clienthttpresponse.getStatusText());
                logger.debug(clienthttpresponse.getBody());
    
                if (clienthttpresponse.getStatusCode() == HttpStatus.FORBIDDEN) {
                    logger.debug("Call returned a error 403 forbidden resposne ");
                    return true;
                }
            }
            return false;
        }
    }
    

    RestTemplate에서 사용하기위한 코드 :

    RestTemplate restclient = new RestTemplate();
    restclient.setErrorHandler(new MyResponseErrorHandler());
    ResponseEntity<String> responseEntity = clientRestTemplate.exchange(
                        URI,
                        HttpMethod.GET,
                        requestEntity,
                        String.class);
                    response = responseEntity.getBody();
    
  2. ==============================

    2.RestTemplate 코드가 표시되지 않지만 RestTemplate에 대한 ResponseErrorHandler를 다음과 같이 설정한다고 가정합니다.

    RestTemplate 코드가 표시되지 않지만 RestTemplate에 대한 ResponseErrorHandler를 다음과 같이 설정한다고 가정합니다.

    RestTemplate restClient = new RestTemplate();
    restClient.setErrorHandler(new MyResponseErrorHandler());
    

    예외는 실제로 handleError 메서드에서 throw됩니다. 내 이전 답변 중 하나에서 CustomResponseHandler를 사용하여 CustomException을 throw하는 방법을 찾을 수 있습니다.

  3. from https://stackoverflow.com/questions/23838752/spring-resttemplate-overriding-responseerrorhandler by cc-by-sa and MIT license