개발
@ControllerAdvice 전역 예외 처리 – REST API에서 메시지·HTTP Status 자동 매핑
스택큐힙리스트
2025. 7. 10. 15:15
반응형
Spring Boot로 REST API를 개발할 때 예외 처리 코드를 매번 컨트롤러에 작성하는 건 유지보수에 큰 부담이 됩니다. 이를 해결하기 위해 사용하는 것이 바로 @ControllerAdvice입니다.
이번 포스팅에서는 @ControllerAdvice를 활용해 전역적으로 예외를 처리하고, 클라이언트에 적절한 메시지와 HTTP 상태 코드를 자동으로 매핑해주는 방법을 소개합니다.
✅ 왜 전역 예외 처리인가?
- 모든 컨트롤러에서 발생하는 예외를 하나의 클래스에서 처리
- 코드 중복 제거
- 일관된 에러 응답 구조 제공
✅ 기본 사용법
@RestControllerAdvice
public class GlobalExceptionHandler {
@ExceptionHandler(IllegalArgumentException.class)
public ResponseEntity<String> handleIllegalArgument(IllegalArgumentException ex) {
return ResponseEntity.badRequest().body(ex.getMessage());
}
@ExceptionHandler(Exception.class)
public ResponseEntity<String> handleException(Exception ex) {
return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR)
.body("예상치 못한 오류가 발생했습니다.");
}
}
- @RestControllerAdvice는 @ControllerAdvice + @ResponseBody 조합
- 예외 종류별로 @ExceptionHandler로 메서드를 나눠 처리
✅ 커스텀 예외 + DTO 응답 구조 만들기
public class ApiErrorResponse {
private String message;
private int status;
private LocalDateTime timestamp;
// 생성자, getter, setter 생략
}
@ResponseStatus(HttpStatus.NOT_FOUND)
public class UserNotFoundException extends RuntimeException {
public UserNotFoundException(String message) {
super(message);
}
}
@ExceptionHandler(UserNotFoundException.class)
public ResponseEntity<ApiErrorResponse> handleUserNotFound(UserNotFoundException ex) {
ApiErrorResponse response = new ApiErrorResponse(
ex.getMessage(),
HttpStatus.NOT_FOUND.value(),
LocalDateTime.now()
);
return ResponseEntity.status(HttpStatus.NOT_FOUND).body(response);
}
- 커스텀 예외를 정의해 도메인 중심 에러 설계 가능
- 일관된 API 에러 포맷으로 응답
✅ 실무에서 자주 쓰는 팁
- @Validated와 함께 사용하면 검증 에러도 처리 가능
- 에러 코드, 로그 추적 ID 등을 포함한 에러 응답 포맷을 설계하면 운영에 유리
- Swagger 문서에서 예외 응답 형식도 함께 명세할 것
반응형