영속성 관리 - 내부동작 방식
반응형
JPA에서 가장 중요한 2가지
1. 객체와 관계형 데이터베이스 매핑(설계)하기(Object Relational Mapping)
2. 영속성 컨텍스트(실제 JPA가 어떻게 동작하는지)
영속성 컨텍스트 ⭐️
- 엔티티를 영구 저장 환경
- EntityManager.persists(entity)
EntityManager 는 영속성 컨텍스트를 관리하는 주체로, persist() 메서드를 통해 엔티티를 영속성 컨텍스트에 넣기.
이를 통해 객체는 영속 상태가 되며, 이후 트랜잭션이 커밋되면 해당 객체가 데이터베이스에 영구히 저장 - 논리적임 개념
눈에 보이는 물리적인 데이터 저장소가 아닌, 객체를 관리하는 논리적인 개념.
엔티티의 생명주기
- 비영속 : 영속성 컨테스트와 전혀 관계가 없는 새로운 상태
new member 객체를 생성하였지만, 영속성 컨테스트(entityManager)에는 넣지 않는 상태 - 영속 : 영속성 컨테스트에 관리되는 상태
new meber 객체 생성하여, em.persit(member); 에서 영속 컨테스트에 넣어 영속 상태로 저장 - 준영속 상태 : 영속 상태였다가 영속성 컨테스트와 분리된 상태
em.detach(member) 를 호출, em.clear(member) 로 컨텍스트를 초기화할 때, em.close() 로 컨텍스트가 닫힐 때 객체가 준영속 상태 - 삭제 상태 : 엔티니가 영속성 컨테스트에서 제거된 상태
em.remove(member) 호출
//비영속
Member member = new Member();
member.setId(100L);
member.setName("HelloJPA");
//영속
System.out.println("===BEFORE===");
em.persist(member);//쿼리가 바로 날라가지 않음
//준영속 상태 - 회원 엔티티를 영속성 컨테스트에서 분리
em.detach(member)
System.out.println("===AFTER===");
tx.commit();//COMMIT 해야 쿼리가 날라감
영속성 컨테스트가 필요한 이유
- 1차 캐시(application - db 사이에 존재) : 그렇게까지 성능 이점을 얻을 수 있는 장점은 없음..
- 1-1) 1차 캐시가 있는 경우 -> 조회용 쿼리를 남기지 않음
- 1-2) 1차 캐시에 없는 경우 -> DB 조회하여 1차 캐시에 저장하여 반환
-
Member member = new Member(); member.setId(100L); member.setName("HelloJPA"); //1차 캐시에 저장됨 System.out.println("===BEFORE==="); em.persist(member);//쿼리가 바로 날라가지 않음 System.out.println("===AFTER==="); //1차 캐시에서 조회 -> 조회용 쿼리를 남기지 않음 Member findMember = em.find(Member.class,100L); tx.commit();//COMMIT 해야 쿼리가 날라감
- 영속 엔티티의 동일성 보장
Member member = new Member(); member.setId(100L); member.setName("HelloJPA"); //1차 캐시에 저장됨 System.out.println("===BEFORE==="); em.persist(member);//쿼리가 바로 날라가지 않음 System.out.println("===AFTER==="); //1차 캐시에서 조회 -> 조회용 쿼리를 남기지 않음 Member findMember = em.find(Member.class,100L); Member findMember2 = em.find(Member.class,100L); //영속 엔티티 동일 - 1차 캐시가 있기에 가능 System.out.println("result= " + (findMember==findMember2)); tx.commit();//COMMIT 해야 쿼리가 날라감
- 트랜잭션을 지원하는 쓰기 지연
- 메모리 내의 SQL 저장소에 쌓아 두었다가, 트랜잭션이 커밋되는 시점에 한꺼번에 데이터베이스에 전달하는 방식
- 변경 감지(dirty checking)
- 엔티티의 초기 상태와 현재 상태를 자동으로 비교하여 변경된 내용을 탐지하고, 트랜잭션 커밋 시점에 데이터베이스에 UPDATE 쿼리를 자동으로 적용하는 기능
준영속 상태
- 영속 상태의 엔티티가 영속성 컨테스트에서 분리(detached)
- 영속성 컨테스트가 제공하는 기능을 사용 못함.(ex. 변경 감지(dirty check)가 발생하지 않음)
try{
//영속
Member member = em.find(Member.class,150L);
member.setName("AAAAA");
//준영속 -> JPA에서 관리안함
em.detach(member);
//entity 매니저 안에 있는 컨테스트 지우기
//em.clear();//준영속상태랑 동일
//영속성 컨테스트 종료
//em.close();
System.out.println("========================");
//트랜잭션 커밋하면 아무것도 일어나지 않음 > update 쿼리 안나감
tx.commit();
}catch (Exception e){
tx.rollback();
}finally {
em.close();
}
반응형
'Study Platform📚 > 김영한👨🏻🏫의 스프링 부트와 JPA 실무 완전 정복 로드맵' 카테고리의 다른 글
연관관계 매핑 기초 (0) | 2024.11.25 |
---|---|
엔티티 매핑 - 객체와 관계형 데이터베이스 매핑(설계)하기(Object Relational Mapping) (2) | 2024.11.20 |
Hello JPA - 애플리케이션 개발 (1) | 2024.10.24 |
자바 ORM 표준 JPA 프로그래밍 - JPA 시작하기(맞는 버전 찾기) (1) | 2024.10.23 |