JPA에서의 프록시는 어떻게 사용하는지 정리해보겠습니다.
간단한 이해를 돕기 위해 이전에 작성했던 포스팅 정보를 첨부해놓겠습니다.
https://applepick.tistory.com/159
프록시 패턴과 데코레이터 패턴
인프런 스프링 고급 원리를 들으면서 프록시 패턴과 데코레이터 패턴을 공부하고 있습니다. "둘이 뭔가 비슷한데? 뭐가 다른거지? 정확하게 어떠한 상황에서 사용해야 할까?"라고 느껴 정리를
applepick.tistory.com
프록시 특징
실제 클래스를 상속받아서 만들어집니다. 사용하는 입장에서 진짜 객체인지 프록시 객체인지 구분하지 않고 사용하면 됩니다.(때에 따라서...) 프록시 객체는 실제 객체의 참조(Target)를 보관합니다.
프록시 객체는 처음 사용할 때 한 번만 초기화
프록시 객체는 원본 엔티티를 상속받습니다. 따라서 타입 체크할 때 중요합니다. ( ==으로 비교 시 프록시 객체와 실제 객체를 비교하여 실패할 수 있습니다. instance of 로 사용)
프록시 객체를 호출 -> 프록시 객체는 실제 객체의 메소드를 호출 순으로 이어집니다.
프록시 객체의 초기화 순서 (하이버네이트 기준)
유저가 getName()을 요청 -> 프록시 객체의 맴버 타겟이 없으면 JPA가 영속성 컨텍스트에게 요청 -> 영속성 컨텍스트가 DB에서 조회 -> 조회된 값으로 실제 Entity 생성 -> 프록시 객체의 target에 진짜 객체를 연결 -> 동일한 객체 조회 시 DB를 다시 거쳐오는 것이 아닌 프록시객체에 있는 값을 반환
주의
위 상황에서 초기화를 영속성 컨텍스트에게 요청을 하였는데 영속성 컨텍스트가 꺼지는 상황이 생기고 다시 조회 요청을 보내면 어떻게될까?
영속성 컨택스트의 도움을 받을 수 없는 준영속 상태일 때, 프록시를 초기화하면 문제가 발생합니다. 그 이유는 영속성 컨텍스트가 관리하던 것이 날라가게되어 LazyInitializationException 발생합니다.
프록시 객체를 초기화 할 때 프록시 객체가 실제 엔티티로 바뀌는 것이 아닙니다. 초기화가 되면 프록시 객체를 통해서 실제 엔티티에 접근가능합니다.
영속성 컨텍스트에 찾는 엔티티가 이미 있으면 getReference()를 호출해도 실제 엔티티를 반환합니다. 그 이유는 JPA는 같은 영속성컨텍스트 트랜잭션 안에서 발생한 객체의 반환 값을 항상 동일해아합니다. (그 반대 상황도 마찬가지)
'혼자 공부하는 것들 > JPA' 카테고리의 다른 글
주문조회 페이징 처리 API 설계하면서 고민했던 점 및 트러블 슈팅 (1) | 2022.09.24 |
---|---|
[Spring + JPA] 동시성 문제를 해결해보자! (0) | 2022.09.09 |
[지구최강 JPA 스터디] 6-7주차 연관관계 매핑 4가지와 단방향, 양방향! (0) | 2022.08.14 |
[지구최강 JPA 스터디] 4-5주차 객체 설계 할때는 단방향으로!? (0) | 2022.07.28 |
[지구최강 JPA 스터디] 2-3주차 몰아서 정리하자! (1) | 2022.07.13 |
댓글