Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

ErrorResponse를 ResponseEntity로 감싸는 구조 #33

Open
corhythm opened this issue May 30, 2022 · 3 comments
Open

ErrorResponse를 ResponseEntity로 감싸는 구조 #33

corhythm opened this issue May 30, 2022 · 3 comments

Comments

@corhythm
Copy link

corhythm commented May 30, 2022

안녕하세요, @cheese10yun
spring-guide 프로젝트를 보다가 GlobalExceptionHandler의 Return 값을 ResponseEntity로 감싸는 구조에 대해서 의문이 들어서 @cheese10yun 님의 의견을 듣고 싶어 이렇게 여쭤봅니다... 왜냐하면 ErrorResponse 자체의 status 값이 ResponseEntity 값의 status 값과 유사한 느낌이 듭니다. GloblaException에서 ResponseEntity 로 해주는 것보다 ErrorCode의 status 값을 status 값을 HttpStatus.INTERNAL_SERVER_ERROR 이런 식으로 변경하고 ErrorResponse 자체만 넘기는 게 낫지 않을까요?

또한, MemberResponse, CouponResponse 이런 reponse dto는 왜 ResponseEntity로 감싸지 않고 그냥 해당 객체만 return 하신 건지도 궁금합니다. 정상적으로 반환이 이뤄질 때는 status code나 message가 따로 필요하지 않다고 생각하셔서 이렇게 하신 건가요?

@cheese10yun
Copy link
Owner

cheese10yun commented Jun 1, 2022

@corhythm

Error Code에 HttpStatus 객체를 갖지 않고 단순 status code int 타입을 갖는 이유

여러 가지 이유가 있는데요. 단일 모듈의 서비스의 경우 프로젝트 내에서 의존관계가 없기 때문에 큰 문제는 없지만 멀티 모듈처럼 구성을 하면 문제가 발생합니다.

xxxx-project
- domain
- service
- internal-api
- external-api
- batch

이런 식으로 모듈을 구성했을 경우 서비스 모듈, 배치 모듈, 도메인 모듈에서 예외를 발생시키기 위해서는 HttpStatus에 대한 의존성이 필요합니다. 그래서 웹 모듈이 아님에도 해당 의존성이 필요해지는 경우가 발생하게 되기 때문에 어느 계층에서 사용하더라도 문제없이 int 값으로 status code를 사용해서 의존성을 줄이는 것입니다.

물론 배치 애플리케이션에서는 Http Status code의 의미가 부족해지는 부분이 있지만, 해당 코드를 기준으로 대략적으로 4xx 클라이언트 사이드 문제 인지, 5xx 우리가 예상하기 어려운 예외인지 구분이 가능하기 때문에 의미는 있다고 생각합니다.

길게 이야기했지만 의존성에 관한 이야기이고 여러 모듈을 구성해서 사용했을 경우 불필요한 의존성을 갖지 않게 하기 위함입니다.

MemberResponse, CouponResponse 경우 ResponseEntity를 감싸지 않은 이유

ResponseEntity 객체로 감싼다는 것은 해당 컨트롤러에서 여러 가지 케이스에 대해서 대체하여 그에 따른 HTTP Status Code를 포함하여 Response Body를 내려주겠다는 의미인데요.

그렇다는 건 개별 컨트롤러 단에서 예외에 대한 핸들링을 진행하겠다는 의미입니다. 그것을 하는 것이 바람직하지 않다고 생각하여 GlobalExceptionHandler를 만든 것인데요. API 서버에서 발생하는 모든 예외를 해당 객체에서 처리하여 통일성 있는 예외 Response를 내려주고 각 개별적인 컨트롤러에 예외에 대한 핸들링에 대한 책임을 부여하지 않아 컨트롤러 계층을 작게 가져가기 위함입니다.

다시 정리하면 일반 컨트롤러에서 ResponseEntity으로 응답하겠다는 것은 예외에 대한 처리까지 해당 컨트롤러에서 진행하겠다는 의미입니다. 쉽게 말해서 개별적인 컨트롤러는 MemberResponse, CouponResponse에 대한 성공 2xx에 대한 응답을 내려주게 객체의 책임을 작게 부여 한 것입니다.

물론 해당 방법이 다 옳은 것은 아니고 제가 의도한 설계 방향성에 대해서 설명드린 것입니다. 프로젝트마다 또 처한 상황에 따라 다르게 적용될 수도 있습니다.

@corhythm
Copy link
Author

corhythm commented Jun 2, 2022

제가 너무 제 프로젝트 기준으로 생각했었네요 ㅠㅠ 이렇게 설계하신 의도를 이제야 이해했습니다. spring-guide가 주변에서 추천을 많이 받아서, 해당 프로젝트 설계 의도를 가능한 한 이해하고 싶어서 질문 드렸는데 친절하게 답변해주셔서 정말 감사드립니다. 😄😃

@cheese10yun
Copy link
Owner

@corhythm

본인 프로젝트에 그러한 방법으로 도입하는 것이 더 효율적이라고 판단이 들면 그렇게 적용하는게 더 좋다고 생각이 듭니다. 저도 코멘트를 작성하니 조금더 생각이 정리되는 부분이 있어서 좋은 경험이였습니다.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants