이 글은 김영한님의 JPA 강의 중 7장 고급 매핑을 듣고 정리한 내용입니다 :)
강의 : 자바 ORM 표준 JPA 프로그래밍 - 기본편
교재 : 자바 ORM 표준 JPA 프로그래밍🤷♀️
: JPA는 객체의 상속과 DB의 슈퍼/서브 타입 관계를 매핑해준다
(관계형 DB에는 상속관계가 없음, 그나마 슈퍼-서브 타입이 객체의 상속과 유사함!)
이 상속관계 매핑에는 3가지 방법이 있는데,
보통은 1번을 사용, 설계가 단순한 경우는 2번을 사용하기도 한다. 그리고 3번은 절대 쓰지 말자-!
이 3가지의 방법은,
우선 엔티티 다 코드 짜고, 그냥 어노테이션만 변경하면 다른 방법으로 바로 바꿀수 있다.
=> 이게 JPA의 편한점이다! 전략 바뀔때마다 코드를 다 다시 짜는 게 아니라, 어노테이션만 변경하면 된다!
@Inheritance(strategy = InheritanceType.JOINED)
@Inheritance(strategy = InheritanceType.SINGLE_TABLE)
@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
: 각각 테이블로 만들고 슈퍼타입에 조인시킴! 기본적으로 주로 사용한다.
슈퍼타입 엔티티에 @Inheritance(strategy = InheritanceType.JOINED)
이때 슈퍼 타입에 속성으로 DTYPE을 두어서, 슈퍼타입 테이블만 보고도 어떤 서브타입인지 구분함 (사실 이 전략에서는 없어도 가능함, 2번에서는 필수)
// 슈퍼 타입 엔티티
@Entity
@Inheritance(strategy = InheritanceType.JOINED) //첫번째 전략!
@DiscriminatorColumn // 기본이름은 DTYPE
public class Item
{
@Id @GeneratedValue
private Long id;
private String name;
}
// 서브 타입 엔티티 중 Album
@Entity
@DiscriminatorValue // 기본은 엔티티 이름 (여기서는 Album)
public class Album extends Item
{
private String artist;
}
: 모든 속성을 하나의 테이블에 몰아넣기, 정말 단순한 설계일 경우 사용한다.
슈퍼타입 엔티티에 @Inheritance(strategy = InheritanceType.SINGLE_TABLE)
여기서는 슈퍼 타입에 속성으로 DTYP을 꼭 설정해주어야 함! (그래야 구분 가능)
// 슈퍼 타입 엔티티
@Entity
@Inheritance(strategy = InheritanceType.SINGLE_TABLE) //두 번째 전략!
@DiscriminatorColumn
public class Item
{
@Id @GeneratedValue
private Long id;
private String name;
}
: 상속도 아니고 그냥 서브타입들을 단일 테이블로 만듦. 이건 그냥 쓰지 말것
// 슈퍼 타입 엔티티
@Entity
@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS) //두 번째 전략!
// @DiscriminatorColumn 이 어노테이션은 필요없음
public abstract class Item
{
@Id @GeneratedValue
private Long id;
private String name;
}
: 객체 만들때 반복되는 몇가지 속성을 저장해두고 필요할때마다 사용하기 위한 어노테이션! (매핑 정보만 상속하는 슈퍼클래스라고 생각하자)
// 속성만 상속하는 슈퍼클래스
@MappedSuperclass
public abstract class BaseEntity // 엔티티 아님!
{
private String createdBy;
private LocalDateTime createdDate;
}
@Entity
public class Member extends BaseEntity {
...
}