private final
을 사용한다.❓JPA에서는
@Entity
어노테이션을 붙이면 JPA가 관리하는 엔티티로 인식되어 편리하게 직접적으로 사용할 수 있을 것 같은데 왜 DTO 클래스와 Entity 클래스를 분리해야할까? 그냥 Entity 클래스를 사용하면 안되는 것일까요?
❗엔티티 클래스는 요청이나 응답 값을 전달하는 클래스로 사용되면 안 된다. 엔티티 클래스는 데이터베이스와 매핑되어있는 핵심 클래스이기 때문이다. 엔티티 클래스를 기준으로 테이블이 생성되고 스키마가 생성된다.
뷰는 비즈니스 로직을 담당하는데 이 뷰는 자주 바뀔 여지가 있다.
만약 엔티티 클래스를 요청이나 응답 값을 전달하는 클래스로 사용한다면 뷰가 변경될 때마다 엔티티 클래스를 매번 변경해야한다. 수많은 서비스 클래스나 비즈니스 로직들이 엔티티 클래스를 기준으로 동작한다. 엔티티 클래스를 변경하면 예상하지 못했던 여러 변화들이 수없이 많이 발생하게 된다.요청이나 응답 값을 전달하는 클래스는 뷰의 변경에 따라 다른 클래스들에게 영향을 끼치지 않고 자유롭게 변경할 수 있는 클래스인 DTO를 사용해야한다. 또한 응답 값으로 여러 테이블들을 조인한 결과값을 줘야 할 경우가 빈번하기 때문에 엔티티 클래스만으로는 응답 값을 표현하기 어려운 경우가 많다. 그래서 엔티티 클래스와 뷰의 결과 값을 전달해주는 DTO는 꼭 분리해서 사용해야한다.
스프링 부트 프로젝트나 다른 유형의 자바 어플리케이션에서 DTO(데이터 전송 개체)를 사용하면 수많은 이점을 얻을 수 있다. DTO는 데이터를 캡슐화하여 애플리케이션의 한 하위 시스템에서 다른 하위 시스템으로 보내는 데 사용되는 개체다. DTO를 사용하는 이유를 간단히 정리하고 넘어가자.
1. 표현과 비즈니스 로직의 분리
계층 분리 : DTO는 프레젠테이션 계층을 비즈니스 논리에서 분리하는데 도움이 된다. 데이터베이스에 사용되는 데이터 구조는 데이터가 UI 또는 외부 API 소비자에 표시되는 방식과 다를 수 있다. 따라서 DTO는 이런 데이터 변환의 중간 지점 역할을 하여 일치/불일치의 문제를 해결할 수 있다.
데이터 집계 : 여러 엔티티 또는 서비스의 데이터를 클라이언트에 최적화된 단일 개체로 결합할 수 있다.
2. 데이터 보안 및 노출 제어
누누이 강조하지만 엔티티를 직접 사용하는 것은 정말 피해야 한다. 엔티티를 직접 사용하면 직렬화를 통해 중요한 데이터나 내부 구현 세부 정보가 실수로 노출될 수 있다. 엔티티 클래스에 민감한 정보(주민등록번호, 패스워드 등)가 포함된 경우 엔티티를 직접 반환하면 클라이언트는 보안 문제를 일으키는 민감한 정보를 취득할 수 있다.
3. 성능 최적화
DTO를 사용하면 네트워크를 통해 필요한 데이터만 전송하여 데이터 페이로드의 크기를 줄일 수 있다. 이는 대역폭과 성능이 중요한 마이크로서비스 또는 웹 서비스에서 특히 중요하다.
4. 지연 로딩 문제
ORM 프레임워크에서 엔티티를 직접 노출하면 지연 로딩 문제가 발생할 수 있다. DTO는 필요한 것만 가져오고 노출함으로써 문제를 방지하는데 도움을 줄 수 있다. 또한 지연 로딩 개념을 제대로 파악하기 위해 필요한 프록시와 엔티티 생명주기, 페치 조인 등을 통한 성능 최적화를 하기에 수월하다.
5. 검증 및 비즈니스 로직 시행
DTO를 사용하여 DTO 및 엔티티에서 비즈니스 로직을 분리하여 유지하면 깔끔하고 이해하기 쉬운 코드를 작성하는데 도움이 된다.
equals()
& hashCode()
둘 다 재정의해야한다.