[JPA] 영속성 컨텍스트

JUJU·2024년 6월 30일
0

Spring Boot

목록 보기
9/13
본 포스트는 김영한 개발자님의 JPA 프로그래밍 강의를 듣고 정리한 것입니다.
※ 코드는 강의에서 사용된 것과 다릅니다.
jaewon-ju Github Address

✏️ 영속성 컨텍스트

영속성 컨텍스트 (Persistence Context)

: 엔티티를 영구 저장하는 환경

  • 애플리케이션 ⇔ DB 사이에서 객체를 보관하는 가상의 환경이다.
  • EntityManager를 통해서 영속성 컨텍스트에 접근할 수 있다.

EntityManager.persist(member);
// member 엔티티를 영속성 컨텍스트에 저장하는 코드



✏️ 주요 기능

영속성 컨텍스트의 주요 기능은 다음과 같다.

  1. 엔티티의 생명 주기 관리
  2. 1차 캐시
  3. 동일성 보장
  4. 변경 감지
  5. 지연 로딩
  6. Transcational Write Behind

1. 엔티티의 생명 주기 관리

영속성 컨텍스트는 엔티티의 생명주기 상태(비영속, 영속, 준영속, 삭제)를 관리한다.

상태설명
비영속(New)엔티티가 생성되었지만, 아직 영속성 컨텍스트에 저장되지 않음
영속(Managed)엔티티가 영속성 컨텍스트에 저장됨
준영속(Detached)엔티티가 영속성 컨텍스트에 저장되었다가 분리됨
삭제(Removed)삭제됨

  • 엔티티를 영속 상태로 만들기 위해서는, Transaction을 시작한 뒤에 em.persist() 메소드를 실행하면 된다.

  • flush() 메소드를 실행하면, 영속성 컨텍스트의 변경내용이 데이터베이스에 반영된다.




2. 1차 캐시

영속성 컨텍스트는 엔티티의 식별자(PK)를 키로 하여 1차 캐시를 유지/관리 한다.

1차 캐시

: 영속 상태의 엔티티를 저장하는 영속성 컨텍스트 내부의 캐시

  • em.persist(member) 를 실행하면 member 엔티티가 1차 캐시에 저장된다.
  • 1차 캐시에 저장되어 있는 엔티티를 조회할 때는 DB에 접근할 필요가 없다!
  • DB에서 엔티티를 조회할 때도 1차 캐시에 해당 엔티티가 저장된다.



3. 동일성 보장

영속성 컨텍스트는 엔티티의 동일성을 보장한다.

Order a = em.find(Order.class, "order1");
Order b = em.find(Order.class, "order1");

System.out.println(a == b); // true 반환



4. 변경 감지 (Dirty Checking)

영속성 컨텍스트는 엔티티의 초기 상태(영속될 때의 상태)를 스냅샷으로 보관하고, 트랜잭션을 커밋할 때 엔티티의 현재 상태와 비교하여 변경된 점이 있으면 데이터베이스에 자동으로 반영한다.

Order orderA = em.find(Order.class, "orderA");
// 1차 캐시에 엔티티 저장 - 스냅샷으로 보관

orderA.setTitle("수박");
orderA.setPrice("10000");
// entity가 수정되었음
// 영속성 컨텍스트가 자동으로 변경을 감지하여 UPDATE 쿼리를 SQL 저장소에 저장한다.

transaction.commit();



5. 지연 로딩

지연 로딩

: 엔티티와 연관된 다른 엔티티를 즉시 로드하지 않고, 실제로 사용될 때 로드하는 방법

이후에 Proxy와 함께 자세히 설명하겠다.




6. Transactional Write-Behind

Transactional Write-Behind

: 엔티티의 변경사항을 즉시 DB에 반영하지 않고, 트랜잭션을 커밋할 때 일괄적으로 반영하는 기술

  • 애플리케이션에서 엔티티의 상태 변경이 발생하면, 변경된 사항들은 영속성 컨텍스트 내에서 추적된다.
  • 해당 변경사항들은 DB에 즉시 반영되지 않고, 메모리 내에 적재된다.
  • 트랜잭션이 커밋되는 시점에 모든 누적된 변경사항이 데이터베이스로 일괄적으로 전송



✏️ flush

플러시란, 영속성 컨텍스트의 변경내용을 데이터베이스에 반영하는 작업이다.
영속성 컨텍스트를 플러시하는 방법은 3가지가 존재한다.

  1. em.flush - 직접 호출
  2. transcation.commit() - 자동 호출
  3. JPQL 쿼리 실행 - 자동 호출

⚠️ 플러시는 영속성 컨텍스트를 비우는 것이 아니다!




REFERENCE

자바 ORM 표준 JPA 프로그래밍 - 김영한 개발자님

profile
개발자 지망생

0개의 댓글

관련 채용 정보