Exception처리 하는 법!!

윤태호·2023년 4월 15일
0

예외처리를 제대로 해본 적이 있나요???

TDD와 마찬가지로 주니어 및 개발 공부를 막 시작한 개발자들은 예외 처리에 대한 깊게 생각을 안하는 것 같다.(지극히 필자의 생각이다.)

  • 우리는 Try Catch까지는 많이 들어봤을 것이다. 물론 Try Catch를 통해 예외처리가 가능하다!! 하지만 Service 및 Controller 계층에서 우리는 가독성이 좋고 깔끔한 코드를 보기를 원한다!(왜냐하면 코드리뷰 및 Refactoring을 할 때 이점이 있기 때문에)
  • 하지만 Try Catch는 코드의 가독성을 떨어트리고 Service 및 Controller에 해당 로직만 있기를 원하는데 그것을 방해한다.
  • 심지어 필자는 이런 고민하기 전에는 if(value == null)이런식으로 처리했다.....

그러면 어떻게 처리할까요???

사실 정답은 없다고 생각합니다. 개발자들은 자기들만의 코드 스타일이 있기 때문입니다. 하지만 저는 Exception Handler를 더 선호합니다. 왜냐하면 개발자는 코드로 대화하고, 협업을 하기 때문입니다. Try Catch 및 If절을 활용하면 결국 Service 로직에 코드를 추가하게 됩니다. 이러면 가독성과 코드간의 결합성과 응집도도 떨어 트린다고 생각합니다.
그래서 필자는 Exception Handler를 도입하였고, 따로 Directory를 두며 예외처리를 할 때는 그 예외에 맞는 클래스를 호출합니다.
아래는 예외를 위한 Directory의 예시입니다.

위의 Directory를 보면 이해하기 어려울 수도 있지만 하나씩 이해해 가봅시다.!!

ValidException??

우리는 @Validated @Valid를 통해서 Controller와 DTO에서의 유효성 검사를 합니다. 그러면 유효성 검사 실패시 어떻게 Exception 처리를 할 것인가??

코드를 보면서 이해해보자!
1. @ControllerAdvice : Controller 전역에서 발생하는 Exceptiond을 잡아 처리해준다.
2. @ExceptionHandler : @Controller, @RestController가 적용된 Bean내에서 발생하는 예외를 잡아서 하나의 메서드에서 처리해주는 기능을 한다. 옆에 괄호안에는 잡고자하는 예외 메소드를 선언합니다.
3. BindingResult : 유효성 검증에 실패한 오류들을 메세지와 함께 담아놓습니다.그래서 makeErrorResponse 메서드를 보면 BindingResult라는 객체에서 메세지와 필드를 받아서 넣어주는 것을 볼 수 있습니다.

GlobalException??

유효성 검증의 예외처리는 위처럼 처리 했지만...유효성뿐만 아니라 Service 및 Repository에서 다양한 예외들이 나올 수 있습니다.
이것을 어떻게 효율적으로 처리 할 수 있을까????라는 고민과 함께 모든 Exception마다 각각 처리하기 매우 귀찮고 시간낭비라 생각한 개발자들은 Java의 강점을 활용합니다.
Enum과 상속을 활용하여 간략화 시킵니다.

Global Exception 코드를 보면 매우 간단합니다. CommonBusiness Exception에서 모든것을 가져와 ResponseEntity로 반환할 뿐입니다.
그러면 CommonBusinessException을 보러가봅시다!

CommonBusinessException

사실 위의 이름을 가진 Exception Class가 Java에 내장된것이 아닙니다. 각자 커스터마이징을 하여 쓰시길 바랍니다!!

이 코드에서 중요시 봐야할 것은 딱 2개입니다.
1. Extends RuntimeException : RuntimeException은 Exception 중 제일 최상위 예외입니다. 즉 모든 예외를 포함하고 있다는 것입니다. 왜 이것을 선언했냐면! CommonBusiness Exception에서 모든 예외를 처리할 수 있게 해주기 위해서입니다.
2. ErrorEnum :

우리는 다양한 예외처리를 해줄 수 있습니다. 그리고 개발자들은 일어날 수 있는 예외들을 정의합니다. Enum을 활용해 각 예외에 대해 선언해놓고 가져다 쓰자는 것입니다!!!

이제 일어날 수 있는 예외들을 Class로 만들자!


이제 다 끝났습니다. 아까 왜 CommonBusinees에서 왜 RunTime Exception을 한지 아시겠습니까?? 이렇게 extends로 상속 받기 위해서입니다!
우리는 예외에 대한 클래스 명을 선언하고 super로 ErrorEnum에 선언해놓은 에러를 넣어주면 끝입니다!!

이렇게 한줄로 예외처리를 깔끔하게 할 수 있습니다!!!

글을 마치며~~~

필자도 예외 처리에 대해 깊게 생각해본적이 없었습니다. 하지만 이번 프로젝트를 통하여 Clean Code와 가독성의 중요성을 느꼈습니다. 왜냐하면 프로젝트는 팀 프로젝트이기에 팀원들도 나의 코드를 읽는 다는 것입니다!! 아직 주니어 및 코린이분들도 꼭 한번 해놓으시면 다음에도 활용하기 편하니 꼭 해보시길 추천드립니다!!!
다음 글은 CQRS Pipe Line 구축기로 돌아오겠습니다.(Kafka, Elastic Search, AWS)등 다양한 내용으로 준비 중이니 기대해주세요 ㅎㅎㅎ

profile
성장하는것을 제일 즐깁니다.

0개의 댓글