DTO vs VO

Jiwoo Kim·2021년 8월 28일
1

척척학사개발자

목록 보기
6/7
post-thumbnail

본 포스팅은 백엔드 스터디 발표 자료로 작성한 내용을 글로 옮긴 것입니다.
상세 예시 코드를 포함한 오리지널 발표 자료는 여기서 보실 수 있습니다.


📌 DTO

정의

DTOData Transfer Object입니다.

말 그대로, 데이터를 전송하는 객체인데,
그 중에서도 레이어프로세스 간 데이터를 전송할 때 사용하는 객체를 의미합니다.

레이어는 MVC 패턴에서 View, Controller, Model을 의미하고,
DTO는 이 레이어들 사이에서 왔다갔다 하는 데이터를 포장한 객체라고 할 수 있습니다.

특성

DTO는 오직 데이터를 전송하는 목적을 가지고 있습니다.
그래서 DTO는 gettersetter 외의 다른 로직이나 메서드를 포함하지 않습니다.
또한 원칙적으로는 변경 가능하다는 특성도 가지고 있습니다.

필요성

하지만 사실, 프로그램 운영에 필요한 진짜 중요한 데이터는 도메인에서 모두 관리합니다.
그럼에도 불구하고, 도메인이 아닌 DTO를 사용해야 하는 이유는 아래와 같습니다.

우선, 데이터를 일일이 도메인에서 꺼내서 view 단에다가 넘겨주면 전송 자원이 낭비됩니다.
View 단에서 필요로 하는 데이터의 형식과 도메인 데이터 형식이 다른 경우가 많기 때문입니다.

두번째로, DTO가 아닌 도메인을 Presentation 레이어에 노출시키면,
필요한 데이터가 아닌 다른 정보들도 함께 노출하게 되면서 캡슐화가 깨집니다.

마지막으로, 도메인이 비즈니스 로직과 Presentation 로직을 같이 수행하면 클래스의 단일 책임 원칙을 위반하게 됩니다.

정리



📌 VO

정의

VOValue Object로,
값을 표현하기 위해 사용하는 객체입니다.

특성

값을 가지는 클래스 중에서도, 속성값 자체가 식별자 역할을 하는 불변 객체를 VO라고 정의합니다.

이게 무슨 말이냐 하면, DB 엔티티의 경우, ID가 식별자 역할을 하는 반면, VO는 모든 필드의 값이 같으면 같은 객체로 판단합니다. 그러기 위해 equals()hashCode() 메서드를 오버라이딩해서 동등성 비교를 구현합니다.

또한, VO는 한 번 객체가 생성되면 모든 속성값이 변하지 않습니다.
객체 자체가 하나의 값을 표현한다고 보기 때문에, 객체가 살아있는 동안 값들을 불변으로 유지하는 것입니다.

뿐만 아니라, VO는 도메인의 일종으로서 역할을 수행할 수 있습니다.
Getter와 setter 외의 메서드를 가질 수 있습니다.

필요성

이런 특징을 가진 VO를, 왜 사용하는지 알아보겠습니다.

우선, VO를 사용하면 객체지향적으로 프로그래밍을 할 수 있습니다.
Entity의 원시 값들을 표현할 때 VO 개념을 적용할 수 있기 떄문입니다.
테이블의 값을 객체로 변환하면서, 테이블 구조 중심이 아닌 객체의 역할과 협력을 중심으로 개발할 수 있게 됩니다.

다음으로, VO를 통해서 우리는 객체를 항상 안전하게 관리할 수 있습니다.
처음 객체를 생성할 때 제약사항과 validation을 거치고, 불변성을 보장하기 때문입니다.

참고로, 컬렉션을 래핑한 일급 컬렉션의 컬렉션 필드를 불변으로 관리하면 일급 컬렉션도 VO가 되는 것이라고 합니다.
모든 일급 컬렉션이 VO인 것은 아니지만, 일급 컬렉션도 VO의 일종이라고 할 수 있는 것입니다.

정리



📌 DTO vs VO

우선 DTO는 데이터 전달을 위한 객체고, VO는 값을 표현하기 위한 도메인입니다.

그렇기에 DTOgetter/setter 외의 로직을 원칙적으로 포함하지 않지만, VO는 로직을 포함합니다.

DTO는 기본적으로 가변 객체고, VO는 불변 객체입니다.

하지만 DTO를 불변객체로 만들거나 DTO 안에 VO 객체를 담으면,
데이터 전송 과정에서도 값의 불변을 보장해서 더 안전하게 기능을 구현할 수 있다는 점을 참고해주시면 될 것 같습니다.

또한, 어느 상황에는 무조건 DTO를 써야 하고, 언제는 또 VO만 써야 한다는 그런 법칙은 따로 없기 때문에
상황과 맥락에 따라서, 필요한 개념을 잘 적용시켜 서비스를 개발하면 되시겠습니다.



참고

Data Transfer Object
ValueObject
[Java] VO(Value Object)란?
VO(Value Ojbect)란 무엇일까?
일급 컬렉션을 사용하는 이유

0개의 댓글