위의 사진과 아래코드를 같이 보자.
지연로딩이란 것은 말그대로 로딩을 지연한다 는뜻이다.
만약 멤버를 호출을 한다고 치자.
뭐 Member m = em.find(Member.class, member1.getId()); 이렇게 호출한다고 치면
select 문을 때릴거고 값을 가져와 m에 넣게 된다.
이때 아무것도 하지 않으면 자동으로 JPA가 Team과 조인을 해서 Team 정보까지 불러온다.
하지만 필요도 없는 Team을 자꾸 호출하기는 싫은거다.
이럴때 아래처럼 Member 클래스에 아래처럼 정의한다.
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name="TEAM_ID")
private Team team;
이렇게 fetch속성을 LAZY로 주게 되면. 지연 로딩이 적용된다.
그냥 Member만 불러오게 되고 find 를 해도 member 테이블만 뒤져서 member만 가져온다.
그때 여기서 System.out.println("m = " + m.getTeam().getClass()); 를 하면 뭐가 나올까??
신기하게도 Team$HibernateProxy$kewiOF6H <- 처럼 프록시 객체가 출력된다....
어케 된걸까?
단순히 Member만 뽑아 주는줄 알았지만 관련된 Team객체도 프록시로만 일단 전달은 해준다는 것이다.
Team 프록시 객체에서 Team 관련 작업을 하는 순간 Team 프록시가 초기화가 되고, 그때 Team select 쿼리도 날라온다.
아래는 예제 코드이고 빨간 글씨에 다다르면 그때 Team 프록시 객체도 초기화 된다.
Team team = new Team();
team.setName("teamA");
Member member1 = new Member();
member1.setUserName("member1");
member1.setTeam(team);
em.persist(team);
em.persist(member1);
em.flush();
em.clear();
Member m = em.find(Member.class, member1.getId());
System.out.println("m = " + m.getTeam().getClass());
System.out.println(" ============================ ");
m.getTeam().getName();
System.out.println(" ================================== ");
tx.commit(); //이시점에 DB 쿼리가 날라감
'Developer' 카테고리의 다른 글
[JPA]불쌍한 고아객체.. (0) | 2020.09.20 |
---|---|
[JPA]CASCADE - persist 1번에 자식까지 (0) | 2020.09.20 |
[JPA]프록시객체 - getReference (와 find 차이) (0) | 2020.09.19 |
[JPA]@MappedSuperClass - 공통된 컬럼 관리 (0) | 2020.09.19 |
[JPA] 상속매핑(Inheritance) 전략 - TABLE_PER_CLASS (0) | 2020.09.19 |