ㅅㅇ
[Spring Boot] 예외 처리 ExceptionHandler 개념 본문
Exception
- 스프링 부트의 예외 처리방식은 크게 2가지가 존재
- @ControllerAdvice 를 통한 모든 Controller 에서 발생할 수 있는 예외처리
- @ExceptionHandler 를 통한 특정 Controller 의 예외처리
⇒ @ControllerException 로 모든 컨크롤러에서 발생한 예외를 정의하고,
@ExceptionHandler 를 통한 발생하는 예외 마다 처리할 메소드를 정의
1. 예외 클래스
- 크게 말하면 로직 상 문제가 있어보인다와 없어보인다의 차이
Checked Exception (그 외 Exception) | UnChecked Exception(RuntimeException) | |
처리 여부 | 반드시 예외 처리 필요 | 명시적 처리 강제하지 않음 |
확인 시점 | 컴파일 단계 문법적으로 이미 명백하게 오류가 범해질 것 그래서 반드시 이뤄져야 하는 것 => try-catch 로 잡아서 예외 처리하거나 상위 메소드로 넘겨주기 | 실행 중 단계 어플리케이션이 가동 실행 중에 발생할 수 있는 에러. 예측 불가능하기에 필수 처리가 불가능 |
예외 발생 시 트랙잭션 | 롤백하지 않음 | 롤백 |
대표 예외 | IQException SQLException | NullPointerException Illegal ArgumentException IndexOutOfBoundException SystemException |
2. 스프링 부트 예외처리 방법
- @ControllerAdvice, @RestControllerAdvice
- 스프링에서 제공하는 어노테이션
- @controller, @RestController 에서 발생하는 예외를 한 곳에서 관리하고 처리할 수있게 하는 어노테이션
- 설정을 통해 범위 지정이 가능하며, Default 값으로 모든 Controller 에 대해 예외 처리를 관리함
- @RestControllerAdvice(basePackages = “io.csy”) 와 같이 패키지 범위를 설정할 수 있음
- 예외 발생 시 json 의 형태로 결과를 반환하기 위해서는 @RestControllerAdvice 를 사용하면 됨.
- @ExceptionHandler
- 예외 처리 상황이 발생하며 해당 Handler 로 처리하겠다고 명시하는 어노테이션
- 어노테이션 뒤에 괄호를 붙여 어떤 ExceptionClass 를 처리할지 설정할 수 있음
- @ExceptionHandler(00Exception.class)
- Exception.class는 최상위 클래스로 하위 세부 예외처리 클래스로 설정한 핸들러가 존재하면, 그 핸들러가 우선처리하게 되며, 처리 되지 못하는 예외처리에 대해 ExceptionClass 에서 핸들링함.
- @ControllerAdvice 안에 설정된 클래스 내에서 메소드로 정의할 수 있지만, 각 Controller 안에 설정도 가능함.
- @ExceptionHandler 는 메소드로 기반으로 어노테이션이기 때문에 메소드가 어느 클래스에 배치되냐에 따라 우선순위를 가지게 된다. 그래서 전역 설정을 하기 위해서는 @ControllerAdvice 쪽에 정의되야 하지만, 지역설정으로 Controller 에 한다면 전역설정보다 지역설정이 더 우선순위를 가진다.
** 스프링 부트 예외 처리의 우선순위
- 글로벌 예외처리 보다 컨트롤러 예외처리가 우선 순위가 더 높다.
- @ExceptionHandler(Exception.class) 보다 @ExceptionHandler(NullPointerException.class) 가 우선순위가 더 높다.
- NullPointerException 는 Exception 에 포함되는 자식 클래스이기 때문에 자식 클래스가 우선순위를 갖는다.
[ 정리 ]
예외처리는 우리가 처리할 수 있는 예외처리가 있고 없는 예외처리가 있다.
이때 우리가 처리할 수 있는 예외처리는 try - catch 를 사용할 수 있다. 예를 들어 데이터가 어긋나 대체 데이터를 넣을 수 있는 상황이라면 우리가 원하는 결과가 나오게 처리 로직을 짜면 되는 것이다.
그러나 우리가 지금까지 다룬 예외처리는 에러 메시지를 어떻게 통합적으로 관리 할 것이냐의 문제이다.
우리가 예외를 예상해 처리하는 로직을 짜는 것이 아니라, 오류가 발생했다고 클라이언트에게 보내는 작업인 것이다. 이 두 부분의 차이를 알고 있어야 한다.
물론 이 핸들러를 통해 오류가 발생하는 것들에 대한 처리도 가능하지만 그렇게 하기에는 각각의 상황에 따라 디테일하게 예외처리를 해줘야 하는데, 사실상 그렇게 한다면 이 통합적 처리라는 것 자체가 무의미하다.
그리고 우리는 자바에서 제공해주는 Exception 처리로 진행하고 있는데, 보통 어프리케이션을 만들 때 자바에서 제공하는 것으로 처리할 수 있는 부분은 처리해주고
그 외의 것 우리가 조금 더 미세 포인트를 잡아야 하는 경우, 우리가 Custom Exception 을 만들어 그것으로 관리해주면 되는 것이다.
3. 에러 응답 예시
- error type, error code, message 를 응답함으로써 Client 에 정확히 어떤 에러가 발생했는지 공유
{
“errorType”:"BadRequest”
“statusCode”:400
“message”:”잘못된 요청입니다.”
}
4. HttpStatus
- HttpStatus 는 Enum 클래스임.
- Enum Class
- 서로 관련있는 상수들을 모아 심볼릭한 명칭의 집합으로 정의한 것
- 클래스 처럼 보이게 하는 상수
HttpStauts(int value, Series series String reasonPhrase) {
this.value = value;
this.series = series; // 이 타입의 에러는 어떤 시리즈에 포함되어 있는지를 의미, 예를 들어 400대는 CLIENT_ERROR 시리즈
this.reasonPhrase = reasonPhrase;
}
EX )
EAD_REQUEST(400, SeriesCLIENT_ERROR, "Bad Request")
HttpStatus(org.springframework.http.HttpStatus) 아래 url 확인
[spring-framework/HttpStatus.java at 4.3.x · spring-projects/spring-framework](https://github.com/spring-projects/spring-framework/blob/4.3.x/spring-web/src/main/java/org/springframework/http/HttpStatus.java#L505)
'SW_STUDY > SpringBoot' 카테고리의 다른 글
[Spring Securtiy] Spring Securtiy FilterChain필터 (0) | 2023.03.08 |
---|---|
[Spring Securtiy] Spring Securtiy 기본 개념 (0) | 2023.03.08 |
[Spring Boot] 예외 처리 ExceptionHandler 예시 (0) | 2023.01.31 |
[Spring Boot] 유효성 검사 & 데이터 검증 Vaildation (0) | 2023.01.28 |
[Spring Boot] 로그 처리 Logback (1) | 2023.01.28 |