인프런 커뮤니티 질문&답변

Junyoung_Choi님의 프로필 이미지
Junyoung_Choi

작성한 질문수

실전! 스프링 부트와 JPA 활용2 - API 개발과 성능 최적화

ManyToMany 관계 동작이 조금 어렵네요..

해결된 질문

작성

·

779

2

강의를 들으면서 토이 프로젝트를 진행중에 있습니다!

사용자(Account)가 평소 여러 주제의 태그(Tag) 중 관심 있었던 주제의 태그를 프로필에 등록하는 기능을 구현 중에 있으며, Account 라는 엔티티와 Tag라는 엔티티가 AccountTag 라는 엔티티로 각각 1:N 매핑된 형태로 N:M 관계를 표현했습니다.

태그 생성 기능은 Gist과 같이 작성했는데, 사용자에서 특정 관심 태그를 삭제하는 remove 동작을 어떻게 구현해야 할 지 감이 잘 오지 않습니다.. 정리하자면 Tag는 그대로 보존하되, 연관된 AccountTag만을 삭제하고 싶습니다. 마음 같아선 영속성 전이를 통해 delete 동작 없이 List에서 remove만 해서 처리하고 싶은데 AccountTag 엔티티와 연관된 객체가 2개 이상이니 Cascade.ALL을 사용하기도 좀 그래서 이런 경우엔 보통 어떻게 처리를 하는지 궁금합니다!

답변 5

2

김영한님의 프로필 이미지
김영한
지식공유자

사실 Tag라는 기능도 하나의 완전히 독립된 기능입니다. 그래서 Account가 중심이 되는 것 보다는 Tag가 중심이 되어서 로직이 이루어져야 합니다.

처음 ORM 설계를 할 때 보통 이런 실수를 많이 하게 됩니다^^!

Account를 중심으로 모든 것을 엮어버리는 것이지요.

예를 들어서 주문이 있으면, Account가 주문을 하니까 Account를 통해서 주문을 처리하고, 또 Account를 통해서 결제를 하니까 Account에 모든 것을 엮는 식으로 설계를 합니다.

하지만 이것은 객체지향 설계를 잘못 한 것일 확율이 높습니다.

Tag도 완전히 독립된 하나의 중요한 기능이고, 주도적으로 동작해야 합니다.

이것을 도메인 주도 설계에서는 AggregateRoot라는 개념으로 설명합니다.

따라서 Tag 관련 기능이 동작할 때는 Tag가 중심이되어야 하고, Account는 Tag를 조회하기 위한 보조수단이 되어야 합니다.

강의 예제에서는 Member가 Orders를 가지고 있는데요. 예제에서 양방향 연관관계 예시를 위해 만든 것이고, 연관관계만 가지고 있지 실제 동작은 모두 Orders를 중심으로 쿼리하고 동작합니다.

정말 중요한 내용인데^^! 질문을 잘 주셨습니다!

객체지향 설계와 관련해서 참고할 만한 책은 

조영호님의 객체지향의 사실과 오해 추천드립니다^^

http://www.yes24.com/Product/Goods/18249021

감사합니다.

0

Junyoung_Choi님의 프로필 이미지
Junyoung_Choi
질문자

아하! 우선 답변을 뒤늦게 확인해서, 그 전에 AccountTag 내에서 ToOne 관계는 모두 fetch Lazy로 설정하고, Account나 Tag에서 ToMany 관계를 호출할 땐 BatchSize를 1000으로 설정한 뒤 다음과 같이 로직을 짰습니다.

양방향 연관관계로 설정한 이유가 Account에서 Tag를 호출할 일이 많을 거 같아서 그런건데, 영한님께서 판단하시기엔 Account에서 Tag를 관리하는 것보다 태그 호출 시마다 account와의 where문을 사용하는 것이 더 괜찮은 구조라는 말씀 맞을까요?

0

김영한님의 프로필 이미지
김영한
지식공유자

Junyoung_Choi님 사실 가장 좋은 것은 Account -> AccountTag 관계를 제거하고 AccountTag -> Account 관계만 남기는 것이 좋습니다.

사실 Account가 AccountTag를 알 필요가 없지요^^!

0

Junyoung_Choi님의 프로필 이미지
Junyoung_Choi
질문자

그러면 결론적으로 Account와 Tag 간의 관계를 제거할 시에는 Cascade를 사용하지 않고, AccountTag 엔티티를 직접 delete한 뒤, Account의 AccountTag 리스트에서도 해당 AccountTag를 제거하면 되는 것 맞습니까?

0

김영한님의 프로필 이미지
김영한
지식공유자

안녕하세요. Junyoung_Choi님^^ 좋은 질문입니다.

사실 영속성 전이를 통해서 처리하고 싶어도, 뭔가 이상한데? 라는 고민이 드실꺼에요.

다음 답변을 보면 해결방인이 보이실꺼에요^^

https://www.inflearn.com/questions/31969

감사합니다.

Junyoung_Choi님의 프로필 이미지
Junyoung_Choi

작성한 질문수

질문하기