JPA Persistence Context


Entity Manger Factory, Entity Manger


次の図に示すように、Webアプリケーションはお客様の要求に応じてEntityManagerを作成します.このEntity ManagerはConnectionでDBにアクセスします.

Persistence Context

  • Persistence Context:Entityを永続的に格納する環境.
  • Persistence Contextは、Entity Managerからアクセスできる論理概念です.したがって、Entity Managerの作成時には、Persistence Contextも作成およびマッピングされます.
  • ライフサイクル

  • 非永続(new/transient):Persistence Contextに関係のない新しいステータス
  • 英領(ホスティング):Persistence Contextで管理されているステータス
  • 準零速(分離):Persistence Contextに保存し、
  • を分離する
  • 削除:削除されました
  • 非永続状態


    オブジェクトは作成のみで、Persistence Contextに保存されていない状態です.
    //객체 생성
    Member member = new Member();
    member.setId("member1");
    member.setUsername("회원1");

    永続状態


    生成されたオブジェクトはPersistence Contextに格納されます.ただし、この場合はDBに格納されるのではなく、DBに格納される時点がTransactionにおけるCommitの時点である.
    ...
    EntityManager em = emf.createEntityManager();
    em.getTransaction().begin();
    //객체를 저장
    em.persist(member);

    準永続および削除


    準永続属性は,オブジェクトをPersistence Contextから分離した状態であり,削除はその名の通りの削除状態である.
    ...
    //객체 분리
    em.detach(member);
    
    //객체 삭제
    em.remove(member);

    Persistence Contextのメリット


    1.メインキャッシュ


    Entity Managerがクエリーを要求すると、まずPersistence Contextのメインキャッシュでクエリーを行います.
    Member member = new Member();
    member.setId("member1");
    member.setUsername("회원1");
    //1차 캐시에 저장
    em.persist(member)
    //1차 캐시에서 조회
    Member findMember = em.find(Member.class, "member1");
    

    プライマリ・キャッシュに値がない場合、データベースはクエリーをプライマリ・キャッシュに保存し、値を返します.
    ...
    Member findMember2 = em.find(Member.class, "member2");
    ...

    ただし、お客様のリクエストが終了すると、エンティティーマネージャが削除されるため、プライマリ・キャッシュのパフォーマンスに大きなメリットはありません.

    2.同一性の保証


    同じ永続Entityを読み込むと、一貫性が保証されます.
    ...
    Member a = em.find(Member.class, "member1");
    Member b = em.find(Member.class, "member1");
    //동일성 비료 : true
    System.out.printIn(a === b);
    ...

    3.書込み遅延(Transactional write-back)、エンティティ登録時に取引をサポート


    JPAは、Commitを行う前に、遅延書き込みのSQLリポジトリにクエリーを格納し、Transaction Commitとともに積み上げたクエリーをDBに送信します.
    ...
    //Transaction 시작
    transcation.begin();
    
    em.persist(memberA);
    em.persist(memberB);
    //현재까지 INSERT SQL을 DB에 보내지 않았다.
    
    //Commit하는 순간 DB에 INSERT SQL을 보낸다.
    transaction.commit();
    ...

    4.変更の検出


    JPAは、EntityのスナップショットをPersistence Contextのプライマリキャッシュに格納します.このスナップショットは、データベースから最初に読み込まれた時点の状態を保存します.
    ...
    Member memberA = em.find(Member.class, "member1");
    //Entity Data 수정
    memberA.setUsername("회원2");
    memberA.setAge(10);
    
    transaction.commit();
    ...
    変更後のCommitでは、現在のEntityとスナップショットを比較してUPDATE SQLを生成し、遅延書き込みのSQLストレージに保存してDBに送信します.

    Flush


    Persistence Contextの変更をDBに反映する操作です.

    Flush発生時

  • 変更検出
  • 遅延書き込みSQLリポジトリに
  • 修正されたEntityを登録
  • 書き込み遅延SQLリポジトリクエリーDB(登録、変更、削除クエリー)
  • へ送信
  • プライマリキャッシュの内容は削除されません.
  • Flush Persistence Context。


    flush():ダイレクトコール
  • トランザクションCommit:Flush自動コール
  • 実行
  • JPQLクエリー:Flush自動コール
  • 注意!

  • Persistence Contextが空ではありません.
  • Persistence Contextの変更をDBに同期します.
  • Transactionという職場が重要です.つまり,Commitより前に同期するだけでよい.
  • じゅんれんぞくじょうたい


    ゼロから準ゼロの状態では、ゼロ状態のEntityはPersistence Contextから分離され、Persistence Contestが提供する機能(Dirty Checkなど)は使用できない.

    準永久状態にする方法

  • em.detach(entity):特定のEntityを準永続状態に変換する
  • em.clear():Persistence Context
  • を完全に初期化
  • em.close():Persistence Context
  • を終了

    [Reference]


    Infolearn金英漢のJava ORM標準JPAプログラミング-基本編:https://www.inflearn.com/course/ORM-JPA-Basic/dashboard