custom exception이란
예외 클래스에는 자바에서 미리 정의한 예외 클래스들이 있다. -> 표준 예외
그리고 개발자가 직접 예외 클래스를 정의하여 사용할 수 있는데 이를 custom exception이라고 한다. ( 사용자 정의 예외 )
비지니스 로직에서 발생가능한 예외를 더 구체적으로 알려주기 위한 목적
참고 링크
https://tecoble.techcourse.co.kr/post/2020-08-17-custom-exception/
custom exception 만드는 팁
설명에 앞서 가능하다면 표준예외를 사용하는 것을 우선 추천한다.
표준예외는 가독성이 좋으며, 충분히 의미 전달이 되며, 메모리 사용량 감소하며, 로딩 시간이 줄어든다.
하지만 custom exception은 설계 측면에서, 유지보수 측면 등 사용하는 다양한 이유가 있다.
1) 이름으로 정보 전달 및 클래스명에 Exception 붙이기
이름으로 어떤 예외가 발생했는지 알 수 있도록 명명할 수 있다.
컨벤션으로 클래스명에 Exception 붙이는 것이 좋다.
2) 메서드가 던지는 모든 예외를 문서화
예외가 발생하는 상황을 구체적으로 문서화 기록
@throws를 이용하면 문서로 기록이 가능하다.
그리고 이름에서 알 수 있는 구체적인 Exception throw하기 ( Exception, RuntimeException 같은 원인을 알기 어려운 상위 클래스 사용 추천 x )
단, unchecked exception은 checked exception과 구분하기 위해 메서드에 throws 선언문은 생략하는 편
/**
*
* @throws NumberFormatException - arg가 숫자형 데이터가 아닌 경우 throw
* @throws SQLException - 예외가 발생할 수 있는 상황 기술 ...
*/
publicvoidfoo(String arg)throws NumberFormatException, SQLException {
}
3) 예외 메시지에 실패 정보 담기
사용자 정의 예외는 표준 예외보다 더 상세한 상세 메시지를 전달가능하다.
- 메세지를 받는 생성자 구현
- toString() 을 Overriding하여 실패 원인에 대한 정보(예외 발생에 영향을 준 모든 필드와 인자의 값)를 추가
다음 코드처럼 IndexOutOfBoundsException 예외에 대한 custom class를 만들어서 더 구체적인 예외 메시지를 전달 할 수 있도록 수정할 수 있다.
public class IllegalIndexException extends IndexOutOfBoundsException {
private static final String message = "범위를 벗어났습니다.";
public IllegalIndexException(List<?> target, int index) {
super(message + " size: " + target.size() + " index: " + index);
}
}
4) 예외 생성 발생 비용 줄이기
상위 클래스 Throwable의 fillInStackTrace() override하면 stack trace 생성 비용을 줄일 수 있다.
보통 Custom Exception은 유효하지 않은 값일 때
하위 비즈니스 로직을 수행하지 못하도록 하기 위한 용도일 때가 많다.
즉 StackTrace가 필요하지 않고 단순히 try-catch로 이후 flow를 제어하거나, Spring 환경에서 ControllerAdvice로 예외를 처리한다든가 하는 상황에서는 불필요한 성능 저하를 막기 위해
아무 trace도 갖지 않도록 직접 fillInStackTrace()를 오버라이딩 처리할 수 있다.
@Override
public synchronized Throwable fillInStackTrace() {
return this;
}
5) 예외 캐싱
static final 키워드를 이용해 예외를 미리 캐싱(로드)해둘 수 있다.
예를 들어 구현해낸 Custom Exception이 stack trace도 갖지 않고, 상황에 따라 정보를 다르게 주는 예외가 아니라 단순하게 메세지만 넘겨준다면 해당 예외를 캐싱해두는 것도 비용 절감의 방법이다.
public class CustomException extends RuntimeException {
public static final CustomException CUSTOM_EXCEPTION = new CustomException("대충 예외라는 내용");
//...
}
6) 예외 응집도 고려
패키지로 따로 사용자 정의 예외를 모아 관리 할 수 있다.
예를 들어 사용자 정의 예외를 사용한다면 예외에 필요한 메시지, 전달할 정보의 데이터, 데이터 가공 메소드들을 한 곳에서 관리할 수 있다. 이는 우리에게 객체의 책임이 분리된 깔끔한 코드를 안겨줄 것이다.
7) 예외 발생 후처리
Spring에서 @RestControllerAdvice를 통해 전역적인 예외 처리가 가능하다.
이 부분은 사용자 정의 예외와 spring을 같이 고려했을 때의 장점이다.
반면
표준 예외는 재사용성이 강하지만 표준 예외의 발생 위치를 알기 어렵다.
예를 들어 IllegalArgumentException 예외가 발생했다면 some 메서드에서 발생했다고 확신할 수 있을까
프로젝트가 커질 수록 중복되는 표준 예외를 발생시키는 곳이 많아질 것이다.
하지만 사용자 정의 예외를 사용하면 이런 혼란스러움을 줄일 수 있다.
@Controller
public class SomeController {
// ...
@PostMapping("/some")
public ResponseEntity<Void> some(@RequestBody SomeRequest request) {
Something something = someService.someMethod(request);
if (somevalidate(something)) {
throw new IllegalArgumentException();
}
SomeExternalLibrary.doSomething(something);
return ResponseEntity.ok().build();
}
// ...
}
'Java' 카테고리의 다른 글
static, final, static final 특징 (0) | 2022.08.20 |
---|---|
PATH, CLASSPATH, BUILDPATH에 대해 (0) | 2021.12.29 |
[Java] 예외처리 시 주의 팁 (0) | 2021.09.19 |
[Java] 시간(Time)/날짜(Date) 제공 클래스 및 시간 비교 (0) | 2021.08.16 |
eclipse - workspace, project, package, class (0) | 2021.01.07 |