Visual Summary - 학습 이미지

ArgumentResolver 가 무엇인가

우선 코드를 한번 보니 HandlerMethodArgumentResolver 라는 인터페이스를 상속받고있고,
그안에 supportsParameter , resolveArgument를 구현하고있다.
알게된 사실
- spring framework 에서 제공하는 인터페이스이다.
- HTTP 요청 즉 request 안에있는 데이터들을 꺼내서 컨트롤러에 정의한 파라미터 값으로 만들어 주는 역할그래서 종류별로 RequestParamResolver , PathVariableResolver , RequestBodyResolver 이런 것들이있고 HandlerMethodArgumentResolver 를 상속 받아서 커스텀 하게 내가 원하는 Resolver를 만들 수 있는 것이다.
즉 /test?name=jaemin → 이렇게 요청이 들어왔을때 우리 컨트롤러는 String name 이렇게 받아야하는데 이때 “jaemin" → String name 으로 변환해 주는게 resolver이다 - supportsParameter 는 parameter가 해당 resolver를 지원하는 여부 확인하는 메서드이다 이게 무슨말인가..? 이해가 안갔는데 코드로 보니 확실하게 이해 할 수 있다, PathVariableResolver 안에 이런식으로 구현이 되어있다고 보면
@Override
public boolean supportsParameter(MethodParameter parameter) {
return parameter.hasParameterAnnotation(PathVariable.class);
}
@PathVariable, @RequestBody 등 어노테이션이 붙어있는데 지금 파라미터가 @PathVariable가 붙어있어? 라고 물어보는 것이다.
그래서 spring 의 동작을 보면 아래와 같은 resovler들이 있을때 해당 parameter에 어떤 어노테이션이 붙어있는지 검증 하는것이다.
PathVariableResolver
RequestParamResolver
RequestBodyResolver
AuthenticationPrincipalResolver
CustomResolver
PathVariableResolver.supportsParameter(parameter)
RequestParamResolver.supportsParameter(parameter)
RequestBodyResolver.supportsParameter(parameter)
...
4. resolveArgument 는 지원을 한다면 parameter를 argument value로 변환, 바인딩 하는 역할 즉 resolver의 역할인 데이터를 변환해준다.
동작시점에 관하여
- Argument Resolver는 Interceptor 가 처리된 후 처리된다.
- Client 가 요청한다(Request).
- Dispatcher Servlet에서 Request를 처리한다.
- 요청을 분석하여 Request에 대한 Hadler Mapping을 한다.
- RequestMappingHandlerAdapter(핸들러 매핑에 맞는 어댑터 결정).
- Interceptor 처리
- Argument Resolver 처리 (등록한 리졸버에 대응되는 파라미터 바인딩)
- Message Converter 처리
- Controller Method invoke
문제 (config 등록)
boolean hasAuthAnnotation = parameter.getParameterAnnotation(Auth.class) != null;
boolean isAuthUserType = parameter.getParameterType().equals(AuthUser.class);
// @Auth 어노테이션과 AuthUser 타입이 함께 사용되지 않은 경우 예외 발생
if (hasAuthAnnotation != isAuthUserType) {
throw new AuthException("@Auth와 AuthUser 타입은 함께 사용되어야 합니다.");
}
구현된 resolver 안에서 @Auth 어노테이션과 AuthUser를 같이쓰게 되어있는데


Cannot invoke "java.lang.Long.longValue()" because the return value of "org.example.expert.domain.common.dto.AuthUser.getId()" is null
라는 에러가 발생하는데 처음엔 왜 null 에러가 발생하지? 했는데 resolver가 무엇인지 알고나니까
해당 어노테이션이 정상적으로 동작하지 않아서 (@Auth 가 어떤 resolver에도 걸리지 않아서) 데이터 바인딩을 해주지 못하니 그 안에 .getId()를 해도 당연히 아무런 데이터를 가져올 수 없는것이다.
해결
컨트톨러에서 정상적으로 사용해도 resovler에서 체크 되지 않았던 이유는 구현한 resolver 는 WebMvcConfigurer 에 addArgumentResolver() 메소드로 구현한 resolver 추가 해주어야 하는데 해주지 않았다.

위 사진 처럼 등록해주면 정상적으로 동작하는 것을 확인 할 수 있다.

'TIL' 카테고리의 다른 글
| 분산lock AOP구현중 원자성 보장을 위한 lua 작성 그리고 그 단점 (0) | 2026.04.15 |
|---|---|
| 네트워크란 무엇인가 ( 네트워크는 마법이 아니다. ) (0) | 2026.03.09 |
| 유닛테스트와 통합테스트 (0) | 2026.03.05 |
| 테스트코드 (0) | 2026.03.04 |
| AOP (0) | 2026.03.03 |