[Spring Boot] JPA 강의 정리-36 (JPQL 페치조인-한계)

Posted by 김성철

SpringBoot - JPA 강의 정리-36(JPQL 페치조인 - 한계)

페치 조인의 한계

- 페치 조인 대상에는 별칭을 줄 수 없다.  
	=====================================================================  
	"select t from Team t join fetch t.member as m"  
	=====================================================================  
	※ 하이버네이트는 가능, 가급적 사용하면 안됨  
	※ 페치조인은 연관된 데이터를 다 긁어옴  
	※ 객체 그래프는 데이터를 전부다 조회해야함  
	※ Team을 조회해서 Member에 대한 조건을 날리고 싶으면 처음부터 Member를 조회하는게 맞음  
	※ 옵션에 따라서 데이터가 지워질 수도 있음  
  
	※ 유일하게 사용하는 경우는 join fetch 를 여러개 사용할 때 사용함  
  
- 둘 이상의 컬렉션은 페치 조인 할 수 없다.  
	1:N도 데이터가 뻥튀기가 되는데 1:N:N여서 데이터가 예상할수 없을 만큼 늘어 날 수 있음.  
  
- 컬렉션을 페치 조인하면 페이징API (setFirstResult, setMaxResults)를 사용할 수 없다.  
	- 일대일, 다대일 같은 단일 값 연관 필드들은 페치 조인해도 페이징 가능  
  
	- 하이버네이트는 경고 로그를 남기고 메모리에서 페이징(매우 위험)  
		DB에서 모든 데이터를 긁어 온 뒤 메모리에서 작업함..  
  
		아래의 쿼리에 페이징이 필요할 경우  
		=====================================================================  
		"select t from Team t join fetch t.member as m"  
		=====================================================================  
  
		아래와 같이 뒤집어서 사용  
		=====================================================================  
		"select m From Member m join fetch m.team t"  
		=====================================================================  
  
		또는 아래와 같이 쿼리를 작성하고 setFristResult , setMaxResult를 지정  
		=====================================================================  
		"select t from Team t"  
		=====================================================================  
		위와같이 작성하고 페이징 api를 사용하면 가능한대 성능이 좋지 않음  
		그래서 위와 같을 때 해당 필드에 @BatchSize(size =100) 옵션을 줌  
  
	- @BatchSize 옵션은 Team 을 가져올 때 laze 로딩으로 불러 올때 연관된 데이터를 지정한 사이즈 만큼 불러옴  
		사이즈는 1000 이하로 사용  
		또한 해당 옵션은 글로벌 세팅으로 지정해줄 수 있음  
		hibernate.default_batch_fetch_size , value = 100  
  
	- DTO로 쿼리 직접 작성해서 사용  

페치 조인의 특징

※ JPA의 70~80% 성능 문제는 fetch join 으로 해결됨  
  
- 연관된 엔티티들을 SQL 한번으로 조회 - 성능 최적화  
- 엔티티에 직접 적용하는 글로벌 로딩 전략보다 우선함  
	@OneToMany(fetch = FetchType.LAZY) //글로벌 로딩 전략  
- 실무에서 글로벌 로딩 전략은 모두 지연 로딩  
- 최적화가 필요한 곳은 페치 조인 적용  

정리

- 모든 것을 페치 조인으로 해결할 수 는 없음  
- 페치 조인은 객체 그래프를 유지할 때 사용하면 효과적  
- 여러 테이블을 조인해서 엔티티가 가진 모양이 아닌 전혀 다른 결과를 내야 하면,  
	페치 조인보다는 일반 조인을 사용하고 필요한 데이터들만 조회해서 DTO로 반환하는 것이 효과적  
	※ 해결방안 세가지  
	- 엔티티를 페치조인으로 조회해온다  
  
	- 페치조인 한 뒤 어플리케이션에서 DTO로 바꿔서 짠다  
  
	- 처음부터 DTO로 짠다