스터디
DTO, VO, Entity 차이
멩주
2022. 10. 22. 17:28
DTO(Data Transfer Object)
- DTO(Data Transfer Object)로서 계층 간 데이터 교환을 위해 사용하는 객체
- 계층간 통신에 사용
- Controller ↔ Service ↔ Repository
- 데이터 교환을 위해 사용하며 로직을 갖지 않는 순수한 데이터 객체이며 Getter/Setter 메소드만을 갖는다.
package com.study.DTO;
public class MemberDTO {
private String name;
private String age;
public MemberDTO(String name, String age) {
this.name = name;
this.age = age;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getAge() {
return age;
}
public void setAge(String age) {
this.age = age;
}
}
VO(Value Object)
- VO(Value Object)는 값 그 자체를 표현하는 객체
- 특정한 값을 나타내는 객체
- 로직을 포함할 수 있으며, 객체의 불변성을 보장합니다.
- 서로 다른 이름을 갖는 VO 인스턴스더라도 같은 속성값을 갖는다면 같은 객체라고 판단할 수 있다.
- 이를 위해 equals와 hashCode를 오버라이딩해야 합니다.
- Equals와 HashCode
public class ColorVO {
private final double red;
private final double green;
private final double blue;
public ColorVO(double red, double green, double blue) {
this.red = red;
this.green = green;
this.blue = blue;
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
ColorVO colorVO = (ColorVO) o;
return Double.compare(colorVO.red, red) == 0 && Double.compare(colorVO.green, green) == 0 && Double.compare(colorVO.blue, blue) == 0;
}
@Override
public int hashCode() {
return Objects.hash(red, green, blue);
}
}


✔️ DTO를 VO처럼 불변 객체로 사용하면 얻을 수 있는 이점
- DTO가 전송하고자하는 데이터가 전송 과정 중 변조되지 않았음을 보장할 수 있다.
Entity
- 실제 DB의 테이블과 매칭되는 객체
- id를 통해 각각의 Entity를 구분
- 속성값으로 구분되지 않는다.
- VO와 마찬가지로 로직을 가질 수 있습니다.
@Entity
@Table(uniqueConstraints = {@UniqueConstraint(name = "userNick_unique", columnNames = {"userEmail", "userNick"})})
public class User {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private int userNo;
@Column(nullable = false)
private String userEmail;
@Column(nullable = false)
private String userPwd;
@Column(nullable = false)
private String userNick;
@Column(columnDefinition = "varchar(20) default 'ROLE_USER'")
@Enumerated(EnumType.STRING)
private UserAuthType userAuth = UserAuthType.ROLE_USER;
}
✔️ Entity를 DTO 대신 사용할 수 있지 않을까?
- 사용할 수는 있지만
- View에서 표현하는 속성 값이 요청에 따라 달라질 수 있는데, 그때마다 Entity의 속성값을 변경하면 영속성 모델을 표현한 Entity의 순수성이 모호해진다.
- Controller에서 쓸 DTO와 Entity는 구분하는 것이 좋다.
정리
DTO | VO | Entity | |
역할 | 계층간 데이터 전송 | 의미있는 값 표현 | DB와 매핑되는 클래스 |
변동 | O | X (불변성) | O |
로직 | X | O(포함할 수 있다) | O(포함할 수 있다) |
이 글을 참고했습니다