부트캠프/Dev

필터에서 예외처리

nameless1004 2024. 8. 20. 21:24

토큰 유효성 검사

jwt 토큰에 유효성에 대해 예외처리를 해주었다.

한가지 생각해야할 것은 필터 단계는 디스패쳐 서블릿 보다 앞에 있기 때문에 RestControllerAdvice나 ControllerAdvice로 예외 처리가 안된다. 여기서 생각해본 것은 예외가 발생한다면 HttpServletResponse에 예외 메세지와 HttpStatus를 반환하고 다음 필터로 넘어가지 않는 방식이 떠올라서 이렇게 구현하였다. 

 

검증 구현부

if (StringUtils.hasText(tokenValue)) { // 토큰이 존재하면 검증 시작
    // JWT 토큰 substring
    String token = jwtUtil.substringToken(tokenValue);
    ErrorInfo errorInfo = new ErrorInfo();
    // 토큰 검증
    if (!jwtUtil.validateToken(token, errorInfo)) {
        jwtUtil.jwtExceptionHandler((HttpServletResponse) response, errorInfo, log
        return;
    }
    // 토큰에서 사용자 정보 가져오기
    Claims info = jwtUtil.getUserInfoFromToken(token);
    User user = userRepository.findByName(info.getSubject())
        .orElseThrow(() -> new NullPointerException("Not Found User"));
    request.setAttribute("user", user);
    chain.doFilter(request, response); // 다음 Filter 로 이동
} else {
    jwtUtil.jwtExceptionHandler((HttpServletResponse) response,
        new ErrorInfo("토큰이 존재하지 않습니다.", HttpStatus.BAD_REQUEST), log);
}

jwtExceptionHandler함수 구현부

public void jwtExceptionHandler(HttpServletResponse response, ErrorInfo errorInfo,
    Logger logger) {
    response.setStatus(errorInfo.getHttpStatus()
        .value());
    response.setContentType("application/json");
    response.setCharacterEncoding("UTF-8");
    try {
        String json = new ObjectMapper().writeValueAsString(errorInfo);
        response.getWriter()
            .write(json);
    } catch (Exception e) {
        logger.error(e.getMessage());
    }
}

ErrorInfo

public class ErrorInfo {
    private String msg;
    private HttpStatus httpStatus;
}