[JPA] 상속관계 매핑

김정연·2024년 5월 6일
0
post-thumbnail

상속 관계 매핑을 공부해본다. (김영한의 JPA 고급매핑)

상속관계 매핑은 객체의 상속관계를 데이터베이스에 어떻게 매핑할지 정하는 것이다.

조인전략

엔티티 각각을 테이블로 만들고 자식이 부모 테이블의 기본키를 받아 pk + fk로 쓰는 전략이다.
테이블은 타입 개념이 없어서 타입을 구문하는 컬럼을 추가해줘야한다.

  • @Inheritance(strategy = InheritanceType.JOINED) 상속 매핑은 부모속성에 어노테이션을 이용해서 알려주고 조인 전략임을 알려주어야한다.
  • @DiscriminatorColumn : 특정 테이블에 저장된 다른 유형의 객체나 엔티티를 구분하는데 사용됌
  • @DiscriminatorValue : 하위 엔티티로 지정되어 저장될 때 상위 클래스의 DiscriminatorColumn 에 저장될 값이다.
@Entity
@Inheritance(strategy = InheritanceType.JOINED)
@DiscriminatorColumn(name = "DTYPE")
public abstract class Item {

    @Id
    @GeneratedValue
    @Column(name = "ITEM_ID")
    private Long id;

    private String name;
    private int price;
}
@Entity
@DiscriminatorValue("A")
public class Album extends Item{

    private String artist;
}

조인전략을 쓰면 테이블이 정규화되고 외래키 참조 무결성 제약조건을 활용할 수 있지만 성능저하가 있을 수 있고,
조회 쿼리가 복잡해진다. 실제로 테이블을 여러개를 left join으로 활용하고 있는데 쿼리를 볼 때마다 어디까지 조회되는지 헷갈린다 ㅠㅠ

단일 테이블 전략

테이블 하나에 모든 값을 넣는 전략이다. 단점은 관련이 없는 컬럼의 경우 null을 허용해줘야 오류가 안생긴다.

@Inheritance(strategy = InheritanceType.SINGLE_TABLE) 단일 테이블임을 알려주고 구분값을 넣어주면된다.

구현 클래스마다 테이블 전략

각각의 테이블에 Item의 id 값을 넣어주는 전략이다.

@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)

not null 제약조건을 쓸 수 있지만 여러 테이블을 함께 조회할 때 성능이 느리다.

MappedSuperclass

만약 부모 클래스와 자식 클래스를 직접 매핑하지 않고 자식 클래스에 부모 클래스의 매핑 정보만 제공하고 싶다면 @MappedSuperclass를 활용하면 된다.

@MappedSuperclass
public abstract class BasicEntity {

    @Id
    @GeneratedValue
    private Long id;
    private String name;
}

BasicEntity를 만들고 자식에 공통적으로 들어가는 속성을 넣어준다.
그리고 자식 엔티티에서는 public class Member extends BasicEntity 해주면 공통 속성이 함께 들어가게 된다.

만약에 물려받은 매핑 정보를 재정의하려면

  • AttributeOverrides or AttributeOverride
    를 사용하고, 연관관계를 재정의 하려면
  • AssociationOverrides or AssociationOverride를 쓰면 된다.
@AttributeOverrides({
        @AttributeOverride(name = "id", column = @Column(name = "MEMBER_ID")),
        @AttributeOverride(name = "name", column = @Column(name = "MEMBER_NAME"))
})
public class Member extends BasicEntity{

여기서 중요한 것은 @MappedSuperclass는 단순히 공통으로 사용하는 정보를 엔티티에 모아주는 역할만 한다.

profile
백엔드 개발자

0개의 댓글