Spring MVC - ArgumentResolver 추가해보기

INCHEOL'S·2021년 3월 8일
0

spring-mvc

목록 보기
1/1

안녕하세요. INCHEOL'S 입니다.

오늘은 Spring MVC의 ArgumentResolver 를 추가하여 Handler Method의 Argument에 내가 원하는 값이 바인딩 되도록 해보겠습니다.

Spring MVC에서 지원하는 여러 ArgumentResolver들이 존재하고 우리가 필요로 하는 대부분의 것들을 지원하지만 하필 Spring에서 지원하지 않는 것들을 필요로 할 때가 있습니다.
이와 관련하여 ArgumentResolver를 추가해보는 예제를 만들어보고자 합니다.

기본적으로 스프링이 지원하는 Handler Argument 목록들을 한번 살펴보세요. 또한 각각의 Handler Argument들을 만들기 위한 ArgumentResolver들도 찾아보시는것도 좋은 공부가 될 것 같습니다.

그럼 시작하겠습니다.

저는 요청을 보낸 User의 IP 주소를 Handler Argument에서 바로 가져올 수 있도록 구성해보겠습니다.

먼저, HandlerMethodArgumentResolver 를 구현한 구현체, 그리고 RemoteAddr이라는 애너테이션을 작성했습니다.

public class MyArgumentResolver implements HandlerMethodArgumentResolver {


    @Override
    public boolean supportsParameter(MethodParameter parameter) {
        return Objects.nonNull(parameter.getParameterAnnotation(RemoteAddr.class));
    }

    @Override
    public Object resolveArgument(MethodParameter parameter, ModelAndViewContainer mavContainer, NativeWebRequest webRequest, WebDataBinderFactory binderFactory) throws Exception {
        HttpServletRequest nativeRequest = (HttpServletRequest) webRequest.getNativeRequest();
        String remoteAddr = nativeRequest.getRemoteAddr();
        return remoteAddr;
    }


}
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.PARAMETER)
public @interface RemoteAddr {
}

RemoteAddr 애너테이션이 붙어 있는 파라미터가 있다면 httpServletRequest의 remoteAddr을 가져와 리턴하도록 단순하게 구성하였습니다.

아! Annotaion을 작성하실 때 주의 사항은 @Retention 정책이 반드시 RUNTIME이여야 합니다. 왜냐하면 JVM에 클래스파일이 메모리에 올라가 기동된 시점이라면 RUNTIME 시점인데 이 시점에 반드시 애너테이션 정보가 살아있어야 우리가 만든 ArgumentResolver에서 정상적으로 판단할 수 있기때문입니다.

그 다음, MyArgumentResolver를 WebMvcConfigurer를 이용하여 ArgumentResolvers 리스트에 추가해줬습니다.

@Configuration
public class WebConfig implements WebMvcConfigurer {

    @Override
    public void addArgumentResolvers(List<HandlerMethodArgumentResolver> resolvers) {
        resolvers.add(new MyArgumentResolver());
    }
}

자, 이제 모든 설정은 끝났습니다.

사용할 컨트롤러를 작성하여 테스트해보겠습니다. 아래와 같이 간단하게 받은 파라미터를 바로 리턴하도록 만들고~

@RestController
@RequestMapping("/argumentResolver")
public class DefaultArgumentController {

    @GetMapping("/remoteAddr")
    public String remoteAddr(@RemoteAddr String ip) {
        return ip;
    }

}

Postman 툴을 이용하여 요청을 날려보겠습니다.

짠!~ 제가 원하는 대로 클라이언트의 아이피가 리턴되었습니다.

아주 간단하죠?!

profile
제주하르방백년초콜릿 먹고싶네요. 아, 저는 백엔드 개발자입니다.

0개의 댓글