상세 컨텐츠

본문 제목

[Spring] Return Value Handler 개념 / Custom Return Value Handler 생성

Spring/개념

by Chan.94 2024. 6. 17. 22:49

본문

반응형

Return Value Handler란


HandlerMethodReturnValueHandler를 줄여서 Return Value Handler라고 한다.

Argument Resolver가 요청 데이터를 처리하듯 Return Value Resolver는 그와 반대로 응답 데이터를 처리한다.

 

Argument Resolver에 대한 내용을 알아야 쉽게 받아 들 일 수 있다.

[Spring/개념] - [Spring] Argument Resolver 개념 / Custom Argument Resolver 생성

 

 

ReturnValueHandler는 Handler(Controller)의 반환값을 가지고 별도의 로직을 수행한 후 Handler Adapter에게 반환한다.

 

 

Custom Value Handler 생성


ReturnValueHandler를 만들기 위해서는 HandlerMethodReturnValueHandler를 상속받은 객체를 만들어야 한다.

supportsReturnType과 handleReturnValue 두 개의 메서드를 구현해야 한다.

public interface HandlerMethodReturnValueHandler {

   boolean supportsReturnType(MethodParameter returnType);

   void handleReturnValue(@Nullable Object returnValue, MethodParameter returnType,
         ModelAndViewContainer mavContainer, NativeWebRequest webRequest) throws Exception;

}
  • supportsReturnType : 어떤 리턴 타입을 처리할 것인지 확인한다.
  • handReturnValue : 리턴 값으로 어떤 작업을 할 것인지 구현한다.

Argument Resolver와 이름만 다르지 수행하는 내용은 거의 동일하다.


Step1. CustomReturnValueHandler 생성 (HandlerMethodReturnValueHandler 상속받은 객체 구현)

Step2. ReturnValueHandler 등록

@Configuration
public class WebConfig implements WebMvcConfigurer{

    @Autowired
    private CustomReturnValueHandler customReturnValueHandler;

    public void addReturnValueHandlers(List<HandlerMethodReturnValueHandler> handlers) {
        handlers.add(customReturnValueHandler);
    }
}

WebMvcConfigurer를 구현한 Configuration 클래스에 생성한 Return Value Hanlder를 등록한다.


RequestMappingHandlerAdapter.java

public class RequestMappingHandlerAdapter extends AbstractHandlerMethodAdapter implements BeanFactoryAware, InitializingBean {

    @Override
    protected ModelAndView handleInternal(HttpServletRequest request, HttpServletResponse response, HandlerMethod handlerMethod) throws Exception {
        ModelAndView mav;
        ...
        mav = invokeHandlerMethod(request, response, handlerMethod);
        ...
        return mav;
    }


    protected ModelAndView invokeHandlerMethod(HttpServletRequest request, HttpServletResponse response, HandlerMethod handlerMethod) throws Exception {
        ...
        ServletInvocableHandlerMethod invocableMethod = createInvocableHandlerMethod(handlerMethod);
        ModelAndViewContainer mavContainer = new ModelAndViewContainer();
        ...

        // Handler 호출
        invocableMethod.invokeAndHandle(webRequest, mavContainer);

        return getModelAndView(mavContainer, modelFactory, webRequest);
    }
}

RequestMappingHandlerAdapter에서 Handler(Controller)가 실행되는 주요 소스이다.

ModelAndViewContainer에 Handler(Controller) 실행 결과가 담기게 된다.

 

ServletInvocableHandlerMethod.java

public class ServletInvocableHandlerMethod extends InvocableHandlerMethod {
    public void invokeAndHandle(ServletWebRequest webRequest, ModelAndViewContainer mavContainer, Object... providedArgs) throws Exception {

        Object returnValue = invokeForRequest(webRequest, mavContainer, providedArgs);

        try {
            this.returnValueHandlers.handleReturnValue(returnValue, getReturnValueType(returnValue), mavContainer, webRequest);
        }
        catch (Exception ex) {
            if (logger.isTraceEnabled()) {
                logger.trace(formatErrorForReturnValue(returnValue), ex);
            }
            throw ex;
        }
    }
}

 

Handler(Controller) 실행 이후 반환값으로 Object 타입의 returnValue가 반환되고 Return Value Handler가 실행되는 것을 확인할 수 있다.

 

앞서 정의한 supportsReturnType를 통해 어떤 ReturnValueHandler를 사용할 것인지 결정되었고 handleReturnValue메서드가 실행된다.

반응형

관련글 더보기

댓글 영역

>