영속성

· JPA
JPA 구현체 대부분은 2차 캐시 기능을 각자 지원했는데 JPA는 2.0에 와서야 2차 캐시 표준을 정의했다. JPA 2차 캐시 표준은 여러 구현체가 공통으로 사용하는 부분만 표준화해서 세밀한 설정을 하려면 구현체에 의존적인 기능을 사용해야 한다. 캐시 모드 설정 2차 캐시를 사용하려면 엔티티에 javax.persistence.Cacheable 어노테이션을 사용하면 된다. @Cacheable은 @Cacheable(true), @Cacheable(false)로 설정할 수 있는데 기본값은 true다. @Cacheable // true @Entity public class Member { ... } 다음과 같이 설정해서 원하는 패키지에만 캐시를 적용할 수 도 있다. @Primary @Bean(name = "e..
· JPA
네트워크를 통해 데이터베이스에 접근하는 시간 비용은 애플리케이션 서버에서 내부 메모리에 접근하는 시간 비용보다 수만에서 수십만 배 이상 비싸다. 따라서 조회한 데이터를 메모리에 캐시 해서 데이터베이스 접근 횟수를 줄이면 애플리케이션 성능을 획기적으로 개선할 수 있다. 그래서 1차, 2차 캐시가 뭔데? 영속성 컨텍스트 내부에는 엔티티를 보관하는 저장소가 있는데 이것을 1차 캐시라 한다. 이것으로 얻을 수 있는 이점이 많지만 일반적인 웹 애플리케이션 환경은 트랜잭션을 시작하고 종료할 때까지만 1차 캐시가 유효하다. 따라서 애플리케이션 전체로 보면 데이터베이스 접근 횟수를 획기적으로 줄이지는 못한다. 하이버네이트를 포함한 대부분의 JPA 구현체들은 애플리케이션 범위의 캐시를 지원하는데 이것을 공유 캐시 또는 ..
· JPA
엔티티의 동등성 비교 영속성 컨텍스트 내부에는 엔티티 인스턴스를 보관하기 위한 1차 캐시가 있다. 이 1차 캐시는 영속성 컨텍스트와 생명주기를 같이 한다. 영속성 컨텍스트를 통해 데이터를 저장하거나 조회하면 1차 캐시에 엔티티가 저장된다. 이 1차 캐시 덕분에 변경 감지 기능도 동작하고, 이름 그대로 1차 캐시로 사용되서어 데이터베이스를 통하지 않고 데이터를 바로 조회할 수도 있다. 영속성 컨텍스트를 더 정확히 이해하기 위해서는 1차 캐시의 가장 큰 장점인 애플리케이션 수준의 반복 가능한 읽기를 이해해야 한다. 같은 영속성 컨텍스트에서 엔티티를 조회하면 다음 코드와 같이 항상 같은 엔티티 인스턴스를 반환한다. 단순이 동등성 비교 수준이 아니라 정말 주소값이 같은 인스턴스를 반환한다. Member memb..
· JPA
JPA 표준 예외 정리 JPA 표준 예외들은 javax.persistence.PersistenceException의 자식 클래스다. 그리고 이 예외 클래스는 RuntimeException의 자식이다. 따라서 JPA 예외는 모두 언체크 예외다. JPA 표준 예외는 크게 2가지로 나눌 수 있다. 트랜잭션 롤백을 표시하는 예외 트랜잭션 롤백을 표시하지 않는 예외 트랜잭션 롤백을 표시하는 예외는 심각한 예외이므로 복구해선 안 된다. 이 예외가 발생하면 트랜잭션을 강제로 커밋해도 트랜잭션이 커밋되지 않고 대신에 javax.persistence.RollbackException 예외가 발생한다. 반면에 트랜잭션 롤백을 표시하지 않는 예외는 심각한 예외가 아니다. 따라서 개발자가 트랜잭션을 커밋할지 롤백할지를 판단하면..
· JPA
순수하게 J2SE 환경에서 JPA를 사용하면 개발자가 직접 엔티티 매니저를 생성하고 트랜잭션도 관리해야 한다. 하지만 스트링이나 J2EE 컨테이너 환경에서 JPA를 사용하면 컨테이너가 제공하는 전략을 따라야 한다. 스프링 컨테이너의 기본 전략 스프링 컨테이너는 트랜잭션 범위의 영속성 컨텍스트 전략을 기본으로 사용한다. 이 전략은 이름 그대로 트랜잭션의 범위와 영속성 컨텍스트의 생존 범위가 같다는 뜻이다. 트랜잭션을 시작할 때 영속성 컨텍스트를 생성하고 트랜잭션이 끝날 때 영속성 컨텍스트를 종료한다. 그리고 같은 트랜잭션 안에서는 항상 같은 영속성 컨텍스트에 접근한다. 스프링 프레임워크를 사용하면 보통 비즈니스 로직을 시작하는 서비스 계층에 @Transactional 어노테이션을 선언해서 트랜잭션을 시작한..
· JPA
객체지향 쿼리와 관련된 다양한 고급 주제를 알아보자. 벌크 연산 엔티티를 수정하려면 영속성 콘텍스트의 변경 감지 기능이나 병합을 사용하고, 삭제하려면 EntityManager.remove() 메서드를 사용한다. 하지만 이 밥벙으로 수백 개 이상의 엔티티를 하나씩 처리하기에는 시간이 너무 오래 걸린다. 이때 여러 건을 한 번에 수정하거나 삭제하는 벌크 연산을 사용하면 된다. // 재고가 10개 미만인 상품의 가격을 10% 상승 String sql = "UPDATE product p SET p.price = p.price * 1.1 WHERE p.stockAmount < :stockAmount"; int resultCount = em.createQuery(sql).setParameter("stockAmoun..
· JPA
고아 객체 제거 JPA는 부모 엔티티와 연관관계가 끊어진 자식 엔티티를 자동으로 삭제하는 기능을 제공하는데 이것을 고아 객체(ORPHAN) 제거라 한다. 이 기능을 사용해서 부모 엔티티의 컬렉션에서 자식 엔티티의 참조만 제거하면 자식 엔티티가 자동으로 삭제한다. @Entiry public class Parent { @Id @GeneratedValue private long id; @OneToMany(mappedBy = "parent", orphanRemoval = true) private List childs; } Parent parent = em.find(Parent.class, id); parent.getChilds().remove(0); // 실제 데이터베이스에서 삭제 orphanRemoval = ..
· JPA
특정 엔티티를 영속 상태로 만들 때 연관된 엔티티도 함께 영속 상태로 만들고 싶으면 영속성 전이 기능을 사용하면 된다. 쉽게 말해서 영속성 전이를 사용하면 부모 엔티티를 저장할 때 자식 엔티티도 함께 저장할 수 있다. JPA는 CASCADE 옵션으로 영속성 전이를 제공한다. @Entity @NoArgsConstructor public class Parent { @Id ... @OneToMany(mappedBy = "parent", cascade = {CascadeType.PERSIST , CascadeType.REMOVE}) // 영속성 전이 private List childrens = new ArrayList(); public void addChild(Child child) { // Child 추가 t..
· JPA
엔티티 매니저(Entity Manager) JPA에서 엔티티 매니저(Entity Manager)는 엔티티를 저장하고, 수정하고, 삭제하고 조회하는 등 엔티티와 관련된 모든 일을 처리한다. 또한 영속성 컨텍스트를 통해 데이터의 상태 변화를 감지하고 필요한 쿼리를 자동으로 수행한다. Spring Data JPA에서는 EntityManager를 자동으로 Bean이 등록되기때문에 직접 사용하지는 않는다. 엔티티 매니저 팩토리와 엔티티 매니저 데이터베이스를 하나만 사용하는 애플리케이션은 일반적으로 엔티티 매니저 팩토리를 하나만 생성한다. 엔티티 매니저 팩토리는 이름 그대로 엔티티 매니저를 만드는 공장인데, 공장을 만드는 비용은 상당히 크다. 따라서 한 개만 만들어서 애플리케이션 전체에 공유하도록 설계되어 있다. ..
beekei
'영속성' 태그의 글 목록