Dev/JPA

영속성 전이와 고아 객체

린네의 2024. 2. 6. 00:40

 

이전 포스팅에서 이어집니다 

2024.02.05 - [개발/jpa] - JPA 에서 프록시 객체와 지연 로딩

 

 

JPA 에서 프록시 객체와 지연 로딩

JPA 를 사용하면서 연관관계를 정의하고, 연관 관계 정의 시 사용하는 지연로딩에 대해 이해하기 위해서는 프록시라는 개념이 무엇인지 확실히 알아야 한다. 해당 게시글에서는 프록시에 대한

zigo-autumn.tistory.com

 


 

1.  CASCADE, 영속성 전이 

  영속성 전이는 연관관계 세팅이나 즉시 로딩과는 전혀 관계가 없는 내용이다. 특정 엔티티를 영속 상태로 만들 때, 연관된 엔티티도 함께 영속 상태로 만들고 싶다면 영속성 전이를 사용할 수 있다.

 즉, 영속성 전이를 사용하면 자동으로 자식 객체까지 persist 가 호출 된다.  여기서 헷갈릴 수 있는 부분이 영속성 전이를 사용하면 연관된 엔티티도 모두 저장이 되기 때문에 CASCADE 가 즉시로딩이라던지, 연관관계 세팅과 관계가 있을 수 있다고 오해하기 쉬운데  영속성 전이를 사용한다고 연관관계가 생긴다던지 즉시 로딩이 지정된다거나 하는 것은 아니다.  단지 연관관계가 있을 경우, 영속성 전이가 지정 되어 있으면 연관관계에 해당하는 객체까지 영속성이 부여되는 편리함만을 제공 한다고 이해해야 한다.

 

 

예시 코드를 보자.

 

  • 엔티티는 Child 와 parent 가 각각 존재한다고 가정한다.
// Child 객체 코드
@ManytoOne(name = "parent_id")
private Parent parent;

// Parent 객체 코드 
@OneToMany(mappedBy="parent", casacde=CascadeType.ALL)
private List<Child> childList = new ArrayList<>();

public void addChild(Child child) {
    childList.add(child);
    child.setParent(this);        

}

// main  코드 
Parent parent = new Parent();
Child child = new Child();


em.persist(parent)

 

  • 결과 :  parent 만 영속성을 지정해도, 연관관계에 있는  child 까지 영속성이 지정되는 것을 확인할 수 있다.

 

 

2.  영속성 전이 옵션  ( CascadeType.[option])

 

 영속성 정의는 다음과 같은 옵션이 있다.

  • ALL : 모두 적용
  • PERSIST : 영속
  • REMOVE : 삭제 
  • MERGE : 병합
  • REFRESH : refresh
  • DETACH : detach




3.  고아 객체  관리 

 고아 객체는 부모 엔티티와 연관 관계가 끊어진 자식 엔티티를 의미한다.  부모 엔티티는 삭제 되었는데 자식 엔티티만 남아 있을 경우, 이는 고아 객체에 해당한다. 이런 고아 객체를 관리하기위해서 orpahnRemoval 라는 전략을 사용할 수 있다.

 사용방법과 주의 사항은 다음과 같다.

 

  • 부모 엔티티와 연관관계가 끊어진 자식 엔티티를 자동으로 삭제 하는 기능으로 DB 에서 데이터가 하나 지워진다
  • orphanRemoval = true  
  • 참조하는 곳이 하나일 때 사용해야 한다
  • 특정 엔티티가 개인 소유일 때만 사용 된다
  • CascadeType.REMOVE 처럼 동작 한다 ( parent 를 하나 지우면 연관된 child 가 지워 진다 ) 

 

  • 사용 방법 
@OneToMany(mappedBy = "parent", cascade = CascadeType.ALL, orphanRemoval = true)
private List<Child> childList = new ArrayList<>();

 

 

4.  부모엔티티를 통해서 자식의 생명주기 관리하기


   이런 고아 객체 관리는  CascadeType.ALL + orphanRemoval=true 를 활성화해서 사용하는데  이를 통해 도메인주도 설계 ( ddd ) aggregate root 개념을 용이하게 구현할 수 있다.  ( aggerate root 는 DDD 에서 서로 관계있는 도메인 모델들의 집합을 의미한다. )



이상으로 프록시 객체부터 지연로딩, 고아 객체의 개념까지 정리를 완료 했다.   다음 게시글에는  값 타입 관련 내용을 작성할 예정이다 : D