JPA : 읽기 전용 성능 최적화
- Spring/JPA
- 2022. 2. 7.
이 글은 자바 표준 ORM JPA를 읽고 정리한 글입니다.
JPA 쿼리 성능 최적화
JPA는 읽기 전용 쿼리를 생성해서 조회 시, 쿼리를 좀 더 최적화 할 수 있다. 이 때의 가장 주된 효과는 1) 스냅샷을 만들지 않게 하거나 2) Flush()를 하지 않게 하면서 성능 최적화를 이끌어 낸다.
읽기전용 엔티티로 성능 최적화
1. 스칼라 타입으로 값을 불러온다.
스칼라 타입으로 엔티티를 불러오면 이 엔티티는 영속성 컨텍스트에서 관리하지 않는다. 따라서 스냅샷도 만들어지지 않고, 더티 체킹 등의 무거운 로직도 스킵된다.
2. 쿼리 힌트를 준다.
스프링 데이터 JPA에서는 @Query에 힌트를 줄 수 있고, 순수 JPA에서는 query.sethint로 읽기 전용 힌트를 줄 수 있다. ReadOnly 힌트를 주면, 만들어진 엔티티는 스냅샷을 생성하지 않는다. 따라서 메모리를 아낄 수 있다. 스냅샷이 없기 때문에 Dirty Checking도 하지 않는다.
읽기전용 트랜잭션으로 성능 최적화
@Transactional의 옵션을 read only = true로 하게 되면, 내부적으로 동작하던 em.flush()가 동작하지 않는다. em.flush()가 동작하지 않는다는 것은 영속성 컨텍스트 내부의 쓰기 지연 저장소에 있는 쿼리들이 나가지 않고, Drity Checking을 하지 않는다는 뜻이다.
읽기 전용 트랜잭션을 사용하면 Flush()만 스킵된다. 트랜잭션의 시작과 커밋은 정상적으로 진행된다.
정리
읽기 전용 트랜잭션을 이용하게 되면 옵션마다 다르지만 Dirty Checking을 Skip하거나 Flush() 동작 등을 하지 않으면서 쿼리를 줄이고, 그 덕분에 좀 더 조회 시 성능이 빨라지는 장점이 있다. 그렇지만 바틀넥은 사실 이런 조회 쿼리보다 수많은 것들이 Join되어 값을 불러와 저장하는 쿼리일 가능성이 높다. 그 말인 즉슨, 읽기 전용 트랜잭션으로 얻을 수 있는 성능 튜닝이 생각보다 효과가 낮을 수도 있다.
'Spring > JPA' 카테고리의 다른 글
JPA : 영속성 컨텍스트와 엔티티의 동일성 (0) | 2022.02.15 |
---|---|
JPA : 동시성 문제 + OSIV (0) | 2022.02.15 |
JPA : Pageable 객체를 이용한 페이징 (0) | 2022.02.06 |
스프링 데이터 JPA : 구현체 확인 (0) | 2022.02.06 |
JPA : @Repository 어노테이션의 기능 (0) | 2022.02.06 |