• 카테고리

    질문 & 답변
  • 세부 분야

    백엔드

  • 해결 여부

    미해결

CascadeType.REMOVE & Detached 상태 질문

19.05.20 18:58 작성 조회수 159

0

안녕하세요 본 강의 후반부에 있던 CascadeType.REMOVE와 엔티티의 Detached로의 상태변화 관련 질문 드립니다!

1.

강의상에 출력된 sql 콘솔 출력 화면을 보니 Post 타입 오브젝트를 remove할 경우 자식 오브젝트 Comment 들에 대한 delete 쿼리가 (총 두번)실행 되었음을 알 수 있습니다.

보통 DDL에서 fk를 생성할 때 ON DELETE CASCADE와 같이 하여 부모 로우가 삭제될 경우 이를 참조하는 자식 로우도 삭제하게 할 수 있는 것으로 알고 있습니다.

명시적으로 DELETE 쿼리가 실행되는 것으로 보아 CasecadeType.REMOVE의 경우는 위 단락에서 말씀드린 fk 제약조건과는 다른 방법으로 보입니다.

제 생각(위 두 방법이 다른것인지)이 맞는지 그리고 CascadeType.REMOVE 방식과 같이 DB가 아닌 EntityManager가 관계를 제어?하게 하는 방법의 이점이 따로 있는 것인지 질문드립니다!

 

2.

DETACHED 

: 강의에서 트랜잭션이 끝나서 Session 밖으로 나왔을때 엔티티의 상태가 DETACHED 상태가 된다고 하셨습니다.

또한 강의 노트상에 Persistent상태에서 Detached 상태로의 전이는 Session.evict(), close() 등의 메서드가 호출되어야 된다고 되어있습니다. 

이 두가지로부터 궁금증이 생겨 질문드립니다.

엔티티상태가 Detached가 되는 것이

1)하이버네이트 EntityManager(Session)가 직접(내부적으로) TransactionManager 타입 오브젝트를 이용하거나해서 트랜잭션을 관리 후 Session.evict()와 같은 메서드를 호출하는 방식으로 자동으로 상태가 변화되는 것인지 

아니면,

2) (스프링 데이터 JPA가 아닌 하이버네이트만 사용하는 상황에서) 개발자가 트랜잭션이 필요하면 TransactionManager를 사용하고 commit() 되었다면 그 때에 직접 Session.evict()를 호출해야하는 것인지가 궁금합니다.

강사님께서 서비스와 리파지토리 레이어에 대해서도 말씀하셨습니다. 이로부터 서비스 메서드 레벨 단위로 트랜잭션이 진행되는 경우를 생각해보았습니다.

위와 같이 트랜잭션이 서비스 메서드 단위로 진행될 경우 1)의 방법보다 2)이 방법으로 진행되는 것이 더 맞는 것 같지만 강의상에서는 (제가 이해하기로는)상태 변화가 저절로 되는 것 같이 이해가 되어 정확히 알고자 질문드립니다!

답변 부탁드리겠습니다.

감사합니다!

답변 1

답변을 작성해보세요.

1

1. 네 하이버네이트에서 DDL을 생성할 때 FK 제약에 그런 옵션까지 넣어주진 않는거 같습니다. 하지만 원한다면 미리 정의해둔 DDL을 맵핑만 하고 하이버네이트가 DDL을 생성하지 않도록 하면 되니까 그런 스키마 설정도 사용하려면 사용할 수 있겠네요. 굳이 EntityManager에 맡길 때의 장점이라면 객체 상태 변화를 EM이 추적할 수 있다는 것 정도가 되겠네요. 

2. 커밋 된 이후에 별다른 메서드 호출을 하지 않으면 해당 객체는 detached 상태가 된거라 생각하시면 됩니다. 보통 트랜잭션을 서비스 계층에 두니까 컨트롤러에서 호출한 서비스의 리턴값으로 어떤 객체를 받았다면 그 객체가 바로 detached 상태일 겁니다. 보통은요.