Embedded Type을 공부하던 중 @ElementCollection과 @Embedded가 비슷하면서도 다른점을 느껴 개인적으로나마 간략하게라도 정리를 해야겠다고 생각하여 블로그를 작성하게 되었다.
먼저 @ElementCollection에 대해 알아보자
(@Embedded의 사용법은 이전 포스트에 기재: https://mason-lee.tistory.com/157 )
@ElementCollection 이란?
@ElementCollection은 JPA에서 사용되는 어노테이션으로 단순한 컬렉션(리스트, 맵, 셋 등)을 사용하여 단일 혹은 복합적인 값 타입(int, String 등)을 저장할 때 사용되는 연관관계 매핑의 한 종류이다.
만약 복합적인 값 타입을 저장할 때에는 @Embeddable을 사용하여 객체로 여러 값 타입(필드)를 저장하여 사용한다.
@ElementCollection의 사용
@Entity
public class Member {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private long id;
//단일 값 타입 사용시
@ElementCollection
//@CollectionTable(name="hobby", joinColumns = @JoinColumn(name= "member_id"))
private List<String> hobby;
//복합 값 타입 사용시
@ElementCollection
@CollectionTable(name="sns", joinColumns = @JoinColumn(name= "member_id", referencedColumnName = "id"))
private List<Sns> sns;
}
@Embeddable
public class Sns{
private String platform;
private String username;
}
@ElementCollection의 이름에서 유추할 수 있듯이 List, Map, Set과 같은 Collection을 이용한 OneToMany 관계매핑시 사용할 수 있다.
단일 값 타입
위의 hobby필드와 같이 단일 값 타입에 대한 관계매핑시에는 다른 객체를 생성하지 않고 @ElementCollection 어노테이션 하나만으로 간단하게 연관관계를 생성할 수 있다.
또한 필요에 따라 @CollectionTable을 사용하여 테이블명과 Member와 연결된 인덱스 넘버의 컬럼명을 지정해줄 수 있다.
복합 값 타입
Sns클래스와 같이 @Embeddable 클래스를 생성해 준뒤 @ElementCollection을 사용하여 관계매핑을 해주면 된다.
이때 반드시 @JoinColumn을 이용하여 메인 클래스(Member)의 PK 컬럼명에 대한 설정을 해주어야 한다.
추가 정보
@ElementCollection 사용시 기존의 Collection을 새로운 Collection으로 대체가 불가능하다.
예를 들어 아래와 같이 기존의 멤버의 ElementCollection 필드에 새로운 Collection으로 대체할 시, 에러가 발생한다.
public void test(){
Member member = repository.findById(1L).get();
List<Sns> sns = List.of(
Sns.builder().platform("Twiter").username("twitUser").build()
);
member.setSns(sns); // 새로운 Collection 등록
repository.save(member); // 에러 발생
}
만약 수정사항이 생긴다면 아래와 같이 기존의 Collection에서 데이터를 수정해 주면 문제가 없다.
public void test(){
Member member = repository.findById(1L).get();
List<Sns> sns = member.getSns();
sns.clear();
sns.add(Sns.builder().platform("Twiter").username("twitUser").build());
repository.save(member);
}
@ElementCollection과 @Embedded 비교
이제 본론으로 들어와서 @ElementCollection과 @Embedded의 차이점을 알아보자.
제일 큰 차이점으로는 @ElementCollection은 연관관계매핑의 한종류이지만 @Embedded는 사실 연관관계 매핑과는 상관이 없다. @Embedded의 경우 분리된 테이블을 연결 시키는 역할이 아닌 분리된 객체에 대한 정보를 하나의 테이블로 관리하기 위한 방식이다.
두 어노테이션을 좀더 정리하자면 아래의 표와 같다.
@ElementCollection | @Embedded | |
연관관계 매핑 | O | X |
컬렉션 | O | X |
단일 테이블 | X | O |
단일 객체(혹은 엔티티) 사용 | △ | X |
단방향 접근 | O | O |
@Embeddable 객체 사용 | △ | O |
'Projects > Personal project - 게시판 만들기' 카테고리의 다른 글
[게시판 프로젝트] 테이블 설계 및 엔티티 관계매핑에 대한 회고 (0) | 2023.08.15 |
---|---|
@Embedd를 활용한 관계 매핑 (0) | 2023.08.14 |
MockMVC - Multipart form data요청 테스트 (0) | 2023.06.10 |
Mock test 단계에서 발생한 MockHttpServletResponse: body is empty (0) | 2023.06.08 |
파일 업로드를 위한 AWS S3 연결 도중 발생한 문제들과 해결방안 (0) | 2023.06.07 |