체크 예외(Checked Exception)
: 예외를 catch해서 체크한후 복구 및 회피등 처리를 해야 하는 예외입니다.언체크 예외(Unchecked Exception)
: 어떤 처리를 할 필요가 없는 예외를 의미합니다. RuntimeException
예외는 모두 언체크 예외입니다.자바 jdk에 내장된 Exception도 유용하지만 서버를 개발하다 보면 다양한 상황에서 다양한 예외를 처리하기 위하여 개발자가 직접 예외를 정의해야 할 수도 있습니다.
throw
키워드를 사용하여 개발자가 임의로 예외를 발생시키면 해당 메서드 밖으로 예외를 던질 수 있습니다. '메서드 밖으로 던진다'라는 의미는 메서드를 호출한 지점으로, 또 그 메서드를 호출한 지점, .... 으로 예외를 받을 때까지 호출한 메서드로 계속 밖으로 던지게 됩니다.
다시 스프링의 @Service
클래스에서 발생한 예외는 @Service
클래스의 메서드들을 호출하는 @Controller
클래스의 헨들러 메서드로 던져지게 됩니다.(@RestControllerAdvice
로 이전 가능)
@Service
public class MemberService{
접근제어자 반환타입 서비스메서드(매개변수){
throw new RuntimeException("메시지");
}
}
하여 서비스 클래스의 메서드에서 예외를 throw하면 원래 @Controller
의 핸들러메스드로 에러를 catch하여야 했지만, @RestControllerAdvice
어드바이스를 통해 모든 컨트롤러의 예외를 통합하여 관리할 수 있습니다.
@RestControllerAdvice
public class GlobalExceptionAdvice{
@ExceptionHandler
@ResponseStatus(HttpStatus.NOT_FOUND)
public ErrorResponse handle예외(RuntimeException e){
System.out.println(e.getMessage());
return null;
}
}
@RestControllerAdvice
: 해당 클래스가 모든 컨트롤러에 던져진 예외를 공통으로 처리하는 어드바이스를 지정합니다.@ExceptionHandler
: 해당 메서드가 매개변수로 전달된 예외를 처리하는 메서드임을 명시합니다.@ResponseStatus(HttpStatus.NOT_FOUND)
: 응답 코드로 HttpStatus.NOT_FOUND를 고정합니다. 만약 응답 코드가 동적이면 해당 에너테이션을 사용하지 않습니다.RuntimeException.getMessage()
: 에러 메세지 내용을 리턴합니다.자바에서도 기본으로 많은 예외들을 제공하지만 개발하는 웹의 환경에 따라 또 다양한 상황에서 개발자가 직접 예외를 정의해서 클라이언트에게 알려줄 수 있다면 좀더 유연하고 구체적으로 프로그래밍을 할 수 있을 것 입니다.
코드와 메세지를 가진 예외를 enum
열거형으로 정의하겠습니다.
public enum 사용자정의코드{
MEMBER_NOT_FOUND(404,"Not Found");
MEMBER_ALREADY_EXIST(405,"Already Exist");
@Getter
private int status;
@Getter
private String message;
사용자정의코드(int status, String message){
this.status = status;
this.message = message;
}
}
enum
열거형은 멤버 변수를 가질 수 있습니다. 그리고 멤버 변수들의 데이터를 가진 상수를 정의할 수도 있습니다.
public class 사용자정의예외 extends RuntimeException{
@Getter
private 사용자정의코드 열거코드;
public 사용자정의예외(사용자정의코드 열거코드){
super(열거코드.getMessage());
this.열거코드 = 열거코드;
}
}
사용자 정의 코드와 사용자 정의 코드를 사용하는 사용자 정의 예외를 모두 정의하였다면 @Service에서 예외를 발생시켜 확인할 수 있습니다.
@Service
public class 서비스{
public 리턴타입 서비스메서드(매개변수){
throw new 사용자정의예외(사용자정의코드.MEMBER_NOT_FOUND);
//사용자정의코드.MEMBER_ALREADY_EXIST도 가능
}
}
사용자 정의 에러를 처리하는 @ExceptionHandler를 정의해야 클라이언트에게 에러를 전송할 수 있습니다.
@RestControllerAdvice
public class 어드바이스{
@ExceptionHandler
public ResponseEntity 에러핸들러(사용자정의예외 e){
System.out.println(e.getExceptionCode().getStatus());
System.out.println(e.getMessage());
return new ResponseEntity<>(HttpStatus.valueOf(e.getExceptionCode(),getStatus()));
}
}
@ResponseStatus 에너테이션을 제거하고 ResponseEntity로 리턴타입을 수정한 것은 다양한 HttpStatus를 지원하기 위해 수정하였습니다.
어떻게 개발자가 임의로 에러를 발생시키고, 또 임의로 에러를 정의하여 사용하는 것에 대하여 학습하였습니다. 많은 상황에서 다양하게 사용될 것임으로 외우기 보단 흐름을 익혀두어야 겠습니다.
없음!