Dto의 사용 범위에 대하여

허진혁·2023년 5월 15일
0

궁금점

Spring Framework로 웹 어플리케이션을 제작하면서, DTO의 사용 범위에 대해 의문이 생겼어요.

DTO의 등장 배경을 보면 MVC 패턴이 있고, Controller가 Model의 데이터들을 통해 View를 제어하는 역할을 할 것이고, 그렇다는 것은 model과 view 사이에서 DTO 이동한다는 거에요.

위의 내용을 바탕으로 생각하면 Controller에서 도메인과와 DTO 변환 과정이 필요해요.

하지만 도메인과와 dto의 변환 과정을 Service에서 하더라도 동작에 전혀 문제는 없어요.

뿐만 아니라, DTO의 목적 자체는 계층간 데이터 이동을 위해 사용되기 때문에 각각 다른 레이어 간에 도메인을 직접적인 노출 하는 것 보다는 DTO를 통해 레이어 간의 데이터 전달이 더 자연스러워요.

그렇다면, 레이어드 아키텍처에서 각 레이어들의 역할부터 찾아보아요.

레이어드 아키텍처

사용 이유

Layered Architecture는 ‘관심사에 분리(Separation of concerns)’가 핵심이에요. 유사한 책임(관심)을 지닌 Layer로 분해하고 각각의 Layer가 하위 Layer에만 의존하도록 구성하는 아키텍처 패턴이에요.

레이어드 아키텍처는 전체적인 시스템의 결합도를 낮추고, 개발자의 인지 과부하를 방지하며 재사용성을 높이고 유지보수성을 향상시키는 것이 목적이에요.

Controller

The Controller layer is the conductor of operations for a request. It controls the transaction scope and manages the session related information for the request. The controller first dispatches to a command and then calls the appropriate view processing logic to render the response.

컨트롤러의 역할은 클라이언트로부터 요청이 들어오면 로그인 관련 정보(세션, 쿠키, 토큰)을 관리하고, 하위 레이어로 전달한 후, 받은 응답을 렌더링 하는 것이에요.

즉, HTTP 요청 파라미터, Body를 Validation 하고 Application(Service) 레이어로 사용자의 요청을 위임 및 받은 응답을 반환하는 역할이에요.

Service

A Service Layer defines an application’s boundary [Cockburn PloP] and its set of available operations from the perspective of interfacing client layers. It encapsulates the application’s business logic, controlling transactions and coor-dinating responses in the implementation of its operations.

서비스의 역할은 어플리케이션의 경계를 정의하고, 비지니스 로직을 캡슐화하는 곳이에요.

Repository

”…a cohesive set of responsibilities for providing access to the roots of AGGREGATES from early life cycle through the end” - Evans

Repository 레이어는 Entity의 영속성을 관장하는 역할이에요. 이로 인해, 표현 계층에서 사용할 도메인 계층의 Aggregates를 DTO로 변환하는 작업을 Repository 단에서 책임지게 하는 것을 지양하자는 의견이 다수 존재했어요.

많은 자료들을 참고했을 때, Repository에서 Entity와 DTO의 변환과정을 담은 곳은 거의 없었어요.

생각 정리

Controller에서 DTO 변환과정을 담을 경우의 문제를 생각해 보았어요.

  1. View에 반환할 필요가 없는 데이터까지 Domain 객체에 포함되어 Controller(표현 계층)까지 넘어와요. 리소스가 그대로 낭비되는 것이에요.
  2. Controller가 여러 Domain 객체들의 정보를 조합해서 DTO를 생성해야 하는 경우, 결국 Service(응용 계층) 로직이 Controller에 포함되요.
  3. 여러 Domain 객체들을 조회해야 하기 때문에 하나의 Controller가 의존하는 Service의 개수가 비대해질거에요.

Service 레이어에서 변환과정을 진행한다면 위와 같은 문제들을 해결할 수 있어요.

레이어간 데이터 전달 목적으로 DTO를 엄격하게 고수한다면 변환 로직이 Service 레이어에서 정의해야 한다고 생각해요. 요청에 대한 응답 역시 Service 레이어의 일부분이기 때문이지요.

그렇다고 항상 Service 레이어에서 변환 과정을 갖는 것이 옳은 것은 아닐거에요. 프로젝트의 규모와 아키텍처의 방향에 따라 선택되어야 할 방안일 뿐인 것이라고 생각해요.

참고자료

웹 MVC 각 컴포넌트 역할
DTO 사용 범위에 대하여
Layered Architecture Deep Dive
10 Common Software Architectural Patterns in a nutshell

profile
Don't ever say it's over if I'm breathing

0개의 댓글