개발지식 먹는 하마 님의 블로그

DTO (Data Transfer Object) 본문

Web

DTO (Data Transfer Object)

devhippo 2025. 3. 31. 19:57

DTO

DTO는 Controller - Service - Repository 계층 간 데이터를 전달하는 객체이다.
(Entity에서 필요한 부분만 꺼내서 포장하는 부분이라고 생각할 수 있을 것 같다.)

Entity를 직접 노출하지 않기 때문에 필드를 보호한다.
또한 필요한 필드만 포함하여 성능을 최적화한다.

 

 DTO와 Entity의 차이

항목 DTO Entity
목적 데이터 전달 데이터 저장
사용 범위 Controller - Service - Repository  JPA, 데이터 베이스
캡슐화 비즈니스 로직 없이 데이터만 포함 비즈니스 로직 포함 가능
변경 가능성 API에 따라 유연한 변경 데이터베이스 스키마 변경 필요
설계 사용자(데이터를 사용하는 개발자) 친화적 데이터베이스 친화적

 

DTO에서 Validation으로 검증하지 못한 부분을 서비스 계층에서 검증할 때,
일부 필드에 대한 검증 로직이 반복된다.
이런 경우 Entity에서 이를 처리해주는 것이 좋다.


예를 들어, 비밀번호를 객체를 다룬다고 하자.

DTO에서 Validation을 이용해 입력받은 비밀번호가 몇 글자 이내인지, 형식은 맞는지는 검증할 수 있다.
그러나 입력 받은 비밀번호가 저장되어있는 비밀번호와 일치하는지는 서비스 계층에서 점검해야 한다.

그리고 두 비밀번호를 비교하는 로직은 서비스 계층의 여러 기능에서 반복되서 사용될 수 있다.
이 부분을 Entity에서 구현해 동일한 로직의 반복을 줄일 수 있다.
따라서, Entity에는 비즈니스 로직을 포함하는 것이 가능하다.


😵‍💫 DTO가 너무 많아...!

DTO는 Entity의 변경 없이 API 설계가 가능하고 유지보수와 보안이 용이하기 때문에

기능에 따라 여러 Request, Response DTO를 생성해서 사용한다.

그런데, 테이블이 많아지면? 기능이 많아지면?
그만큼 사용하는 DTO의 개수가 늘어나게 된다.

createADto
createBDto
...

updateADto
updateBDto
...

이런 식으로 말이다.

그렇다면 이를 어떻게 좀 더 간소화해서 관리하는 방법이 없을까?

없다.

공통적인 내용을 구현하고 이를 상속하는 방법을 생각해볼 수는 있다.
그러나 이 방법은 치명적인 단점이 있다.
부모에 변경사항이 생기면 자식들에 대해서 이를 모두 수정해주어야 한다는 수정의 불편함이다.

따라서 DTO의 개수가 늘어나는 것은 어쩔 수 없이 안고 가야하는 부분이다.
다만 많은 DTO를 정리하는 방법은 2가지로 생각해볼 수 있다. (by. 튜터님)

  1. inner class 사용
  2. 기능별 pakage로 분리 

DTO를 설계할 때, 캡슐화를 고려하는 것도 좋지만
DTO로 받은 데이터를 사용자가 어떻게 사용하는지도 중요하다는 점을 유념하며 설계하도록 하자 😉