본문 바로가기

JPA

영속성 컨텐스트란 ?

Entity

  • DB의 테이블과 매칭이 되는 개념
public class AccountHistory {
    @Id
    @GeneratedValue
    @Column(name = "ID")
    private Integer id;

    @ManyToOne(cascade = CascadeType.PERSIST, fetch = FetchType.LAZY)
    @JoinColumn(name = "ACCOUNT_NO", referencedColumnName = "ACCOUNT_NO")
    private Account account;

    @Column(name = "DEPOSIT_WITHDRAWAL_YN", nullable = false)
    @ColumnDefault("'N'")
    private String depositWithdrawalYn;

    private Integer depositAmt;

    @Column(name = "TRANSACTION_DATE")
    @CreatedDate
    private LocalDate transactionDate;

}

그렇다면 DB Table이 아니고 이름이 Entity인 이유는 무엇일까?

  • 모든 케이스에서 테이블 컬럼을 다 다루지 않는다
  • 어떤 경우에는 특정 컬럼만 다루는 경우도 있을 수 있다
  • 그런 경우에 대비해서 다음과 같이 엔티티 클래스를 하나 더 만들 수 있다
public class AccountHistoryDto {
    @Id
    @GeneratedValue
    @Column(name = "ID")
    private Integer id;

    @ManyToOne(cascade = CascadeType.PERSIST, fetch = FetchType.LAZY)
    @JoinColumn(name = "ACCOUNT_NO", referencedColumnName = "ACCOUNT_NO")
    private Account account;

}

Entity Manager

  • 엔티티를 관리하는 역할을 수행하는 클래스
  • 엔티티 매니저 내부에 **영속성 컨텍스트(Persistence Context)**라는 걸 두어서 엔티티들을 관리

영속성 컨텍스트(Persistence Context)

  • 엔티티를 영구 저장하는 환경
  • 애플리케이션과 데이터베이스 사이에서 객체를 보관하는 논리적인 개념
  • EntityManager를 통해서 영속성 컨텍스트에 접근
  • 여러 엔티티 매니저가 하나의 영속성 컨텍스트를 공유할 수도 있다

어떻게 동작?

  • 영속성 컨텍스트 안에는 쓰기 지연 SQL 저장소라는 공간이 따로 존재
  • 트랜잭션이 커밋 되기 직전까지 모든 쿼리문은 영속성 컨텍스트 내부의 쓰기 지연 SQL 저장소에 저장
  • 트랜잭션이 커밋되는 순간 모든 쿼리가 한 방에 날아간다
  • 트랜잭션 내부에서 오류가 나서 롤백을 해야한다면 애초에 날리지도 않을 쿼리를 날리지도 않는다.

Entity Manager Factory

출처 : https://ultrakain.gitbooks.io/jpa/content/chapter3/chapter3.1.html

  • 엔티티 매니저는 여러 스레드가 동시에 접근하면 동시성 문제가 발생하므로 스레드 간에 절대 공유하면 안 된다.
  • 따라서 엔티티 매니저는 하나를 공유하면 안 되고, 상황에 따라서 계속해서 만들어줘야한다
  • 바로 엔티티 매니저 팩토리(공장)가 이런 역할을 수행한다
  • 엔티티 매니저 팩토리는 엔티티 매니저와 달리 여러 스레드가 동시에 접근해도 안전하다. 단순히 엔티티 매니저만 생성하기 때문이다
  • 보통 DB당 하나의 엔티티 매니저 팩토리를 생성해서 공유해서 사용하다. 생성 비용이 굉장히 크기 때문이다

'JPA' 카테고리의 다른 글

QueryDSL은 왜 Q-Class를 사용할까?  (0) 2023.07.25
1. JPA란  (0) 2022.01.18