개요
현재 SecurityFilterChain이다. whiteList는 모든 요청을 허용하고, adminList는 ADMIN권한을 가진 사람에게만 허용하고,
그 외의 요청은 모두 USER권한이 필요하도록 설정해놓았다.
이러한 권한 검증을 마친 후 filter가 작동되게끔 설계했는데,
taskhandler에서 자동으로 작동하는 헬스체크가 실패하고있다. filterChain에서 권한 처리를 다 했는데, 왜 이런 현상이 발생할까?
원인
이 문제를 해결하려면 인증과 인가의 차이를 이해해야 한다.
인증(Authentication): 사용자의 신원을 검증하는 과정, jwtFilter에서 토큰을 검증하여 사용자를 인증하는 역할 수행
인가(Authorization): 인증된 사용자의 권한을 확인하여 리소스 접근을 허용/거부함, securityFilterChain에서 url별 권한을 설정해 접근 제어
예를 들면, JwtFilter에서 Token복호화로 SecurityContext에 현재 사용자의 정보를 저장하면, 해당 사용자의 정보를 바탕으로 인가 로직을 수행하는 것이다.
현재 SecurityFilterChain에서 인가 로직은 정상적으로 적용되어 있지만,
인증 필터(jwtFilter)에서 whiteList를 처리하지 않으면 헬스체크 요청같은 whiteList url도 jwt검증을 거치게 되므로 인증 오류가 발생하였다.
해결
현재 JwtAuthenticationFilter는 OncePerRequestFilter를 상속받아 사용하고 있다.
OncePerRequestFilter에서는 특정 엔드포인트에서 인증필터를 사용하지 않도록 whiteList와 비슷한 메서드를 제공한다.
이 메서드를 jwtFilter에 오버라이딩 해주면 해결된다!
public class JwtAuthenticationFilter extends OncePerRequestFilter {
@Override
protected boolean shouldNotFilter(HttpServletRequest request) {
String path = request.getRequestURI();
List<String> whiteList = jwtSecurityProperties.secret().whiteList();
return whiteList.contains(path);
}
@Override
protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain chain)
throws IOException {
String bearerJwt = request.getHeader("Authorization");
if (bearerJwt == null) {
filterExceptionHandler.sendErrorResponse(response, HttpStatus.BAD_REQUEST, "JWT 토큰이 필요합니다.");
return;
}
...
OncePerRequestFilter는 이렇게 shoudNotFilter와 skipDispatch가 false인 요청에 대해서만 인증을 수행한다.
이제 정상적으로 헬스체크를 완료한 것을 볼 수 있다!
'팀 프로젝트 > cheerha.project' 카테고리의 다른 글
LazyInitializationException (0) | 2025.03.25 |
---|---|
Spring Security와 JWT (0) | 2025.03.18 |
최종 프로젝트 KPT 회고 (0) | 2025.03.17 |