[2019] Spring JPA의 사실과 오해 (youtube.com)
이 글에서는 위 동영상에서, Entity 보다는 Dto를 우선이라는 챕터에 대해 느낀 점을 작성합니다.
Entity 보다는 Dto를 우선
우리가 ORM을 사용하면서 Entity를 조회하는 경우가 많다. Entity를 통째로 가져온다면, N + 1 문제라던가, 불필요한 칼럼까지 가져오는 문제가 발생할 수 있다. 이는 성능 이슈의 요소를 포함한다.
따라서 우리는 Entity를 조회할 필요가 있는지 따져볼 필요가 있다.
- Entity를 수정해야 하는가?
- 단지 데이터의 조회만 필요하는가?
조회칼럼 최소화 하기
QueryDSL에서는 as 표현식으로 만약 이미 알고있는 정보가 있다면 이를 제거할 수 있다.
Select 컬럼에 Entity 자제
Entity 자체를 쿼리 하지 말고, 필요한 칼럼만 DTO를 사용해서 조회하는 것이 성능적으로 좋다.
특히 @OneToOne 관계에서는 Lazy Loading이 안 되므로 무조건 N+1문제가 발생한다.
그런데, Entity간 연관관계를 맺으려면
반대 Entity가 있어야하지 않나요?
이 부분이 나도 궁금했던 부분이고, 이 글을 작성하게 된 계기가 됐다.
이런 Store 엔티티가 있다고 치고,
@Entity
@Getter
@Setter
public class Store extends BaseTimeEntity {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
@Column(name = "store_id", columnDefinition = "uuid", updatable = false)
private UUID storeId;
@OneToOne
@JoinColumn(name = "user_id", nullable = false)
private User user;
아래와 같이 Store를 만드는 코드가 있다면, 엔티티를 인자로 넣어줘야 하는거 아닌가? 싶었고 항상 그래왔다.
(아래 코드의 경우 User가 들어간다.)
public Store toEntity(User user) {
return Store.builder()
.user(user)
.storeName(storeName)
.storeNumber(storeNumber)
.category(category)
.build();
}
하지만 생각해보면 그럴 필요가 없다. 왜냐하면 연관된 Entity의 save를 위해서는 반대편 Entity의 ID만 있으면 된다.
public Store toEntity(Long userId) {
return Store.builder()
.user(new User(userId))
.storeName(storeName)
.storeNumber(storeNumber)
.category(category)
.build();
}
위와 같은 느낌으로 수정하면 된다.
즉, 우리는 엔티티를 저장하기 위해 다른 연관 관계의 엔티티를 통째로 불러올 필요가 없다.
느낀 점
뭔가 DTO를 적극 활용해서, 필요한 칼럼만 추출하는 습관을 가져야겠다고 느꼈다.
'Development > Reflection' 카테고리의 다른 글
[Reflection] Kafka를 활용한 이벤트 기반 아키텍처 구축 #우아콘2023 #우아한형제들 (4) | 2024.10.09 |
---|---|
[Reflection] ㄷㄷㄷ: Domain Driven Design과 적용 사례공유 / if(kakao)2022 (1) | 2024.09.08 |
[Reflection] [우아콘2020] 수십억건에서 QUERYDSL 사용하기 (0) | 2024.09.03 |