em.persist(객체명);을 통해서 영속성 컨텍스트(엔티티 매니저)에 객체를 저장한 상태
1차 캐시에 올라가서 JPA가 관리하는 상태
준영속 (detached)
영속성 컨텍스트에서 분리된 상태
삭제 (removed)
삭제된 상태
실제 DB 삭제를 요청하는 상태
Membermember=newMember();//객체를 생성한 상태 (비영속)member.setId(3L);member.setUsername("memberC");System.out.println("=== BEFORE ===");//출력 순서 1em.persist(member);//객체를 저장한 상태 (영속)System.out.println("=== AFTER ===");//출력 순서 2tx.commit();//실제 커밋할 때 쿼리 실행, 출력 순서 3em.detach(member);//회원 엔티티를 영속성 컨텍스트에서 분리, 준영속 상태em.remove(member);//객체를 삭제한 상태 (삭제) //member를 영속성 컨텍스트에서 분리시켰기 때문에 SELECT 쿼리가 발생한다.MemberfindMember=em.find(Member.class,3L);
1차 캐시
데이터베이스의 한 트랙잭션 안에서만 효과가 있다.
위의 이유때문에 크게 이점을 얻을 수 있는 장점이랄꺼까지는 없지만 그래도 비즈니스 로직이 복잡할 때는 어느 정도 도움이 된다.
//객체를 생성한 상태 (비영속)Membermember=newMember();member.setId(4L);member.setUsername("memberD");em.persist(member);tx.commit();//1차 캐시에서 가져오기 때문에 SELECT가 발생하지 않는다.MemberfindMember=em.find(Member.class,4L);System.out.println(findMember.getId());//출력 : 4System.out.println(findMember.getUsername());//출력 : memberD
동일성 보장
영속 엔티티의 동일성 (identity) 보장 => 같은 트랜잭션에 한해서 보장, 1차 캐시의 기능
MemberfindMember1=em.find(Member.class,5L);MemberfindMember2=em.find(Member.class,5L);System.out.println(findMember1==findMember2);//동일성 비교 : true
트랜잭션을 지원하는 쓰기 지연 (transactional write-behind)
Membermember6=newMember();member6.setId(6L);member6.setUsername("memberF");em.persist(member6);//INSERT 발생 안함Membermember7=newMember();member7.setId(7L);member7.setUsername("memberG");em.persist(member7);//INSERT 발생 안함tx.commit();//INSERT 2건 발생
변경 감지(Dirty Checking)
MemberfindMember=em.find(Member.class,3L);// 영속 엔티티 조회findMember.setUsername("memberC-1");//name 변경//em.persist(findMember); => 사용안함tx.commit();//UPDATE 발생
지연 로딩(Lazy Loading)
/*
추후 작성
*/
준영속 상태
em.detach(entity);//특정 엔티티만 준영속 상태로 전환 em.clear();//영속성 컨텍스트를 완전히 초기화 em.close();//영속성 컨텍스트를 종료