일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | 4 | |||
5 | 6 | 7 | 8 | 9 | 10 | 11 |
12 | 13 | 14 | 15 | 16 | 17 | 18 |
19 | 20 | 21 | 22 | 23 | 24 | 25 |
26 | 27 | 28 | 29 | 30 | 31 |
- 오버라이딩
- 인터페이스
- objecterror
- 코드트리조별과제
- ocp
- java
- http 메시지 컨버터
- html form
- DI
- 오블완
- 테스트코드
- fielderror
- 코딩테스트
- 서블릿
- 스프링
- 백준
- 프록시
- 코드트리
- 스프링컨테이너
- equals()
- 참조변수
- HttpServletResponse
- @configuration
- 티스토리챌린지
- 싱글톤
- JSON
- 의존관계
- 추상클래스
- 다형성
- 김영한
- Today
- Total
minOS
자바 예외 이해 - 체크 예외 기본 이해 본문
체크 예외 기본 이해
- Exception 과 그 하위 예외는 모두 컴파일러가 체크하는 체크 예외이다. 단 `RuntimeException` 은 예외로 한다.
- 체크 예외는 잡아서 처리하거나, 또는 밖으로 던지도록 선언해야한다. 그렇지 않으면 컴파일 오류가 발생한다.
체크 예외 전체 코드
package hello.jdbc.exception.basic; import lombok.extern.slf4j.Slf4j; import org.assertj.core.api.Assertions; import org.junit.jupiter.api.Test; @Slf4j public class CheckTest { @Test void checked_catch(){ Service service = new Service(); service.callCatch(); } @Test void checked_throw(){ Service service = new Service(); Assertions.assertThatThrownBy(()-> service.callThrow()) .isInstanceOf(MyCheckedException.class); } /** * Exception을 상속받은 예외는 체크 예외가 된다. * */ static class MyCheckedException extends Exception{ public MyCheckedException(String message) { super(message); } } /** * Checked 예외는 * 예외를 잡아서 처리하거나, 던지거나 둘 중 하나를 필수로 선택해야 한다. */ static class Service{ Repository repository = new Repository(); /** * 예외를 잡아서 처리하는 코드 */ public void callCatch(){ try { repository.call(); } catch (MyCheckedException e) { log.info("예외 처리 , message={} ", e.getMessage(),e); } } /** * 체크 예외를 밖으로 던지는 코드 * 체크 예외는 에외를 잡지 않고 밖으로 던지려면 throws 예외를 메서드에 필수로 선언해야 합니다. * @throws MyCheckedException */ public void callThrow() throws MyCheckedException { repository.call(); } } static class Repository{ public void call() throws MyCheckedException { throw new MyCheckedException("ex"); } } }
Exception을 상속받은 예외는 체크 예외가 된다.
static class MyCheckedException extends Exception{ public MyCheckedException(String message) { super(message); } }
- MyCheckedException는 Exception을 상속받았다. Exception을 상속받으면 체크 예외가 된다.
- 참고로 `RuntimeException` 을 상속받으면 언체크 예외가 된다. 이런 규칙은 자바 언어에서 문법으로 정한 것
- 예외가 제공하는 여러가지 기본 기능이 있는데, 그 중에 오류 메시지를 보관하는 기능도 있다. 예제에서 보는 것처럼 생성자를 통해서 해당 기능을 그대로 사용하면 편리하다.
예외를 잡아서 처리하는 코드@Test void checked_catch(){ Service service = new Service(); service.callCatch(); }
- service.callCatch()에서 예외를 처리했기 때문에 테스트 메서드까지 예외가 올라오지 않는다.
실행 순서 도식화Repository.call()` 에서 `MyUncheckedException` 예외가 발생하고, 그 예외를 `Service.callCatch()`
에서 잡는 것을 확인할 수 있다.
실행 결과
-실행 결과 로그를 보면 첫줄은 우리가 남긴 로그가 그대로 남는 것을 확인할 수 있다.- 두 번째 줄 부터 예외에 대한 스택 트레이스가 추가로 출력된다.
- 이 부분은 로그를 남길 때 로그의 마지막 인수에 예외 객체를 전달해주면 로그가 해당 예외의 스택 트레이스를 추가로 출력해주는 것이다.
log.info("예외 처리 , message={} ", e.getMessage(),e);
마지막에 있는 `e` 부분이다.
체크 예외를 잡아서 처리하는 코드
public void callCatch(){ try { repository.call(); } catch (MyCheckedException e) { log.info("예외 처리 , message={} ", e.getMessage(),e); } }
- 체크 예외를 잡아서 처리하려면 `catch(..)` 를 사용해서 예외를 잡으면 된다.
- 여기서는 `MyCheckedException` 예외를 잡아서 처리한다.catch는 해당 타입과 그 하위 타입을 모두 잡을 수 있다
- 'catch` 에 `MyCheckedException` 의 상위 타입인 `Exception` 을 적어주어도 `MyCheckedException` 을
잡을 수 있다.
- `catch` 에 예외를 지정하면 해당 예외와 그 하위 타입 예외를 모두 잡아준다.
- 물론 정확하게 `MyCheckedException` 만 잡고 싶다면 `catch` 에 `MyCheckedException` 을 적어주어야 한다.
예외를 처리하지 않고, 밖으로 던지는 코드
@Test void checked_throw(){ Service service = new Service(); Assertions.assertThatThrownBy(()-> service.callThrow()) .isInstanceOf(MyCheckedException.class); }
-`service.callThrow()` 에서 예외를 처리하지 않고, 밖으로 던졌기 때문에 예외가 테스트 메서드까지 올라온다.
- 테스트에서는 기대한 것 처럼 `MyCheckedException` 예외가 던져지면 성공으로 처리한다.
체크 예외를 밖으로 던지는 코드
public void callThrow() throws MyCheckedException { repository.call(); }
- 체크 예외를 처리할 수 없을 때는 `method() throws 예외` 을 사용해서 밖으로 던질 예외를 필수로 지정해주어야 한다. 여기서는 `MyCheckedException` 을 밖으로 던지도록 지정해주었다.
체크 예외를 밖으로 던지지 않으면 컴파일 오류 발생
- `throws` 를 지정하지 않으면 컴파일 오류가 발생한다.
- 체크 예외의 경우 예외를 잡아서 처리하거나 또는 `throws` 를 지정해서 예외를 밖으로 던진다는 선언을 필수로해주어야 한다.
체크 예외를 밖으로 던지는 경우에도 해당 타입과 그 하위 타입을 모두 던질 수 있다
- throws` 에 `MyCheckedException` 의 상위 타입인 `Exception` 을 적어주어도 `MyCheckedException` 을 던질 수 있다.
-`throws` 에 지정한 타입과 그 하위 타입 예외를 밖으로 던진다.- 물론 정확하게 `MyCheckedException` 만 밖으로 던지고 싶다면 `throws` 에 `MyCheckedException` 을 적어주어야 한다.
체크 예외의 장단점
체크 예외는 예외를 잡아서 처리할 수 없을 때, 예외를 밖으로 던지는 `throws 예외` 를 필수로 선언해야 한다. 그렇지
않으면 컴파일 오류가 발생한다. 이것 때문에 장점과 단점이 동시에 존재한다.
- 장점: 개발자가 실수로 예외를 누락하지 않도록 컴파일러를 통해 문제를 잡아주는 훌륭한 안전 장치이다.
- 단점: 하지만 실제로는 개발자가 모든 체크 예외를 반드시 잡거나 던지도록 처리해야 하기 때문에, 너무 번거로운 일이 된다. 크게 신경쓰고 싶지 않은 예외까지 모두 챙겨야 한다. 추가로 의존관계에 따른 단점도 있다.
'TIL > 김영한의 스프링 DB 1편' 카테고리의 다른 글
자바 예외 이해 - 체크 예외 활용 (1) | 2024.12.09 |
---|---|
자바 예외 이해 - 언체크 예외 기본 이해 (2) | 2024.12.09 |
스프링 부트의 자동 리소스 등록 (1) | 2024.12.07 |
트랜잭션 문제 해결 - 트랜잭션 AOP 적용 (0) | 2024.12.07 |
트랜잭션 문제 해결 - 트랜잭션 AOP 이해 (0) | 2024.12.07 |