[JPA] 프록시와 즉시로딩, 지연로딩

leehyunjon·2022년 7월 19일
0

JPA

목록 보기
8/10

프록시

연관관계를 가지는 객체를 조회할때, 연관관계는 가지지만 사용하지 않는 연관관계 객체를 함께 조회한다는 것은 효율적이지 못하다.

그렇기 때문에 사용하는것이 지연로딩으로 연관관계 객체를 사용하는 순간 해당 객체 조회 쿼리를 데이터베이스에 요청한다.(영속성 컨텍스트에 없다고 가정하면)

그렇다면 어떤 객체를 조회했을 때, 지연로딩으로 설정한 연관관계 객체는 객체가 아니라 무엇인가?

Member member = em.find(Member.class, 1);

Team team = member.getTeam();	//??
String name = team.getName();	//실제 객체 조회 SELECT 쿼리 요청

지연로딩으로 설정한 연관관계 객체는 가짜 엔티티로써 프록시 객체라고 하는 것이다.

프록시(Proxy)

프록시란 실제 객체 상속받는 클래스로 써 실제 객체 처럼 보이는 껍데기(가짜) 객체이다.

프록시 객체는 실제 객체 참조(target)을 가지고 있는데, target을 가지고 실제 객체처럼 사용할 수 있다.

target은 프록시 객체가 처음 만들어 졌을 때는 비어있고 JPA에 의해 초기화 요청을 받았을 때 데이터베이스에서 실제 객체를 가져와 target이 실제 객체를 참조한다.

메서드

  • em.find() : 실제 엔티티를 조회할 때 사용
  • em.getReference() : 데이터베이스 조회를 미루는 가짜 엔티티를 조회

실행 순서

JPA를 이용한 hibernate proxy는 아래와 같이 실행된다.

Member member = em.getReference(Member.class, 1); //프록시 객체

String name = member.getName(); //실제 객체 요청
  1. 프록시 객체에서 getName()메서드 호출
  2. 초기 프록시 객체는 target이 비어있기 때문에 JPA는 영속성 컨텍스트에 target 초기화 요청
  3. 영속성 컨텍스트가 데이터베이스를 조회
  4. 실제 엔티티 생성 및 저장
  5. 프록시 객체의 target이 실제 엔티티를 참조하게 되고 target.getName()을 통해 member.getName()과 같은 결과를 반환받는다.

프록시 특징

  • 프록시 객체의 target이 한 번 초기화 되면 초기화 과정은 다시 할 필요 없다.
  • 프록시 객체가 초기화된 것은 target이 실제 객체를 참조하는 것이지 프록시 객체가 실제 객체가 된것이 아니다.
  • 프록시 객체의 클래스 타입과 실제 객체타입은 다르다.(== : false)
  • 영속성 컨텍스트에 프록시 객체가 참조하는 엔티티가 존재한다면 프록시 객체가 아닌 실제 엔티티가 반환
    • 영속성 컨텍스트에 id=1인 member가 존재한다면 em.getReference(Member.class, 1)는 실제 id=1인 member 반환.

즉시로딩, 지연로딩

즉시로딩

public class Member{
	@Id
    Long id
    
    @ManyToOne(fetch = FetchType.EAGER)
    Team team;
}

엔티티를 조회할때 연관관계 엔티티는 JOIN을 통해 함께 조회된다.

@ManyToOne, @OneToOne 인 곳. 즉, 연관관계가 하나인 곳에서 즉시로딩이 default

하지만 연관관계 조회 효율성을 위해 지연로딩으로 설정하는 것을 추천하고 효율에 따라서 설정한다.

지연로딩

public class Team{
	@Id
    Long id
    
    @OneToMany(fetch = FetchType.LAZY)
    List<Member> members = new ArrayList<>();
}

엔티티를 조회할때 해당 엔티티만 조회되고 연관관계 엔티티를 사용하는 순간 조회된다.

@OneToMany, @ManyToMany 인 곳. 즉, 컬렉션인 연관관계인 곳에서 지연로딩이 default


Reference

https://ict-nroo.tistory.com/131

https://ultrakain.gitbooks.io/jpa/content/chapter8/chapter8.1.html

https://ultrakain.gitbooks.io/jpa/content/chapter8/chapter8.2.html

profile
내 꿈은 좋은 개발자

0개의 댓글