✍️
이런 걸
배워요!
JPA의 기본기를 탄탄하게 다질 수 있습니다.
JPA의 내부 동작 방식을 이해할 수 있습니다.
객체와 DB 테이블을 올바르게 설계하고 매핑할 수 있습니다.
실무에서 자신있게 JPA를 사용할 수 있습니다.
인프런 강의 : https://www.inflearn.com/course/ORM-JPA-Basic
강의 자료 :
https://github.com/braverokmc79/jpa-basic-lecture-file
소스 :
https://github.com/braverokmc79/ex-jpa-13-1
https://github.com/braverokmc79/jpa-shop
[6] 고급 매핑
22. 상속관계 매핑
강의:
https://www.inflearn.com/course/lecture?courseSlug=ORM-JPA-Basic&unitId=21705&tab=curriculum
목차
• 상속관계 매핑
• @MappedSuperclass
• 실전 예제 - 4. 상속관계 매핑
상속관계 매핑
• 슈퍼타입 서브타입 논리 모델을 실제 물리 모델로 구현하는 방법
• 각각 테이블로 변환 -> 조인 전략
• 통합 테이블로 변환 -> 단일 테이블 전략
• 서브타입 테이블로 변환 -> 구현 클래스마다 테이블 전략

주요 어노테이션
• @Inheritance(strategy=InheritanceType.XXX)
• JOINED: 조인 전략
• SINGLE_TABLE: 단일 테이블 전략
• TABLE_PER_CLASS: 구현 클래스마다 테이블 전략
• @DiscriminatorColumn(name=“DTYPE”)
• @DiscriminatorValue(“XXX”)
1) @Inheritance(strategy = InheritanceType.JOINED) 추가시
Item
@Entity
@Inheritance(strategy = InheritanceType.JOINED)
public abstract class Item {
@Id @GeneratedValue
private Long id;
private String name;
private int price;
}
Album
@Entity
@Setter
@Getter
public class Album extends Item{
private String artist;
}
Book
@Entity
@Setter
@Getter
public class Book extends Item{
private String author;
private String isbn;
}
Movie
@Entity
@Setter
@Getter
public class Movie extends Item{
private String director;
private String actor;
}
Hibernate:
create table Album (
artist varchar(255),
id bigint not null,
primary key (id)
)
Hibernate:
create table Book (
author varchar(255),
isbn varchar(255),
id bigint not null,
primary key (id)
)
Hibernate:
create table Item (
id bigint not null,
name varchar(255),
price integer not null,
primary key (id)
)
Hibernate:
create table Movie (
actor varchar(255),
director varchar(255),
id bigint not null,
primary key (id)
)
다음은 개인 적으로 가장 좋은 방식
2) @Inheritance(strategy = InheritanceType.JOINED) 추가후
@DiscriminatorColumn 어노테이션 설정
=> @DiscriminatorColumn 어노테이션 설정하면 DTYPE 추가 된다.
@Entity
@Inheritance(strategy = InheritanceType.JOINED)
@Setter
@Getter
@DiscriminatorColumn
public class Item {
@Id @GeneratedValue
private Long id;
private String name;
private int price;
}
package jpashop.home;
import javax.persistence.EntityManager;
import javax.persistence.EntityManagerFactory;
import javax.persistence.EntityTransaction;
import javax.persistence.Persistence;
import jpashop.home.domain.Movie;
public class JpaMain {
public static void main(String[] args) {
EntityManagerFactory emf=Persistence.createEntityManagerFactory("hello");
EntityManager em=emf.createEntityManager();
//JPA 의 모든 데이터 변경은 트랜잭션 안에서 실행 되어야 한다.
EntityTransaction tx=em.getTransaction();
tx.begin();
try {
Movie movie =new Movie();
movie.setDirector("aaa");
movie.setActor("bbb");
movie.setName("바람과함께 사라지다");
movie.setPrice(10000);
em.persist(movie);
tx.commit();
}catch(Exception e) {
tx.rollback();
}finally {
em.close();
}
emf.close();
}
}
=>실행시 결과
만약에 Movie 클래스에 @DiscriminatorValue("M") 어노테이션 // 추가시 타입명 축약 됨


조인 전략
• 장점
• 테이블 정규화
• 외래 키 참조 무결성 제약조건 활용가능
• 저장공간 효율화
• 단점
• 조회시 조인을 많이 사용, 성능 저하
• 조회 쿼리가 복잡함
• 데이터 저장시 INSERT SQL 2번 호출
다음과 같이 SINGLE_TABLE 으로 변경만 하면 단일 테이블 전략 처리 되며 DTYPE 은 반드시 추가 된다.
@Inheritance(strategy = InheritanceType.SINGLE_TABLE)
create table Item (
DTYPE varchar(31) not null,
id bigint not null,
name varchar(255),
price integer not null,
artist varchar(255),
author varchar(255),
isbn varchar(255),
actor varchar(255),
director varchar(255),
primary key (id)
)

단일 테이블 전략 (InheritanceType.TABLE_PER_CLAS ) (사용하지 말것 )
• 장점
• 조인이 필요 없으므로 일반적으로 조회 성능이 빠름
• 조회 쿼리가 단순함
• 단점
• 자식 엔티티가 매핑한 컬럼은 모두 null 허용
• 단일 테이블에 모든 것을 저장하므로 테이블이 커질 수 있다. 상
황에 따라서 조회 성능이 오히려 느려질 수 있다.

구현 클래스마다 테이블 전략
• 이 전략은 데이터베이스 설계자와 ORM 전문가 둘 다 추천X
• 장점
• 서브 타입을 명확하게 구분해서 처리할 때 효과적
• not null 제약조건 사용 가능
• 단점
• 여러 자식 테이블을 함께 조회할 때 성능이 느림(UNION SQL 필요)
• 자식 테이블을 통합해서 쿼리하기 어려움
23. Mapped Superclass - 매핑 정보 상속
강의 :
https://www.inflearn.com/course/lecture?courseSlug=ORM-JPA-Basic&unitId=21706&tab=curriculum

@MappedSuperclass
• 상속관계 매핑X
• 엔티티X, 테이블과 매핑X
• 부모 클래스를 상속 받는 자식 클래스에 매핑 정보만 제공
• 조회, 검색 불가(em.find(BaseEntity) 불가)
• 직접 생성해서 사용할 일이 없으므로 추상 클래스 권장
@MappedSuperclass
• 테이블과 관계 없고, 단순히 엔티티가 공통으로 사용하는 매핑
정보를 모으는 역할
• 주로 등록일, 수정일, 등록자, 수정자 같은 전체 엔티티에서 공통
으로 적용하는 정보를 모을 때 사용
• 참고: @Entity 클래스는 엔티티나 @MappedSuperclass로 지
정한 클래스만 상속 가능
import java.time.LocalDateTime;
import javax.persistence.MappedSuperclass;
import lombok.Getter;
import lombok.Setter;
@MappedSuperclass
@Getter
@Setter
public abstract class BaseEntity {
private String createdBy;
private LocalDateTime createdDate;
private String lastModifiedBy;
private LocalDateTime lastModifiedDate;
}
@Entity
public class Member extends BaseEntity{
@Id @GeneratedValue
private Long id;
@Column(name="USERNAME")
private String username;
}
24. 실전 예제 4 - 상속관계 매핑
강의 :
https://www.inflearn.com/course/lecture?courseSlug=ORM-JPA-Basic&unitId=21707&tab=curriculum
요구사항 추가
• 상품의 종류는 음반, 도서, 영화가 있고 이후 더 확장될 수 있다.
• 모든 데이터는 등록일과 수정일이 필수다.



BaseEntity
import java.time.LocalDateTime;
import javax.persistence.MappedSuperclass;
import lombok.Getter;
import lombok.Setter;
@MappedSuperclass
@Getter
@Setter
public abstract class BaseEntity {
private String createdBy;
private LocalDateTime createdDate;
private String lastModifiedBy;
private LocalDateTime lastModifiedDate;
}
Item
import java.util.ArrayList;
import java.util.List;
import javax.persistence.Column;
import javax.persistence.DiscriminatorColumn;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.Inheritance;
import javax.persistence.InheritanceType;
import javax.persistence.ManyToMany;
import lombok.Getter;
import lombok.Setter;
@Entity
@Getter
@Setter
@Inheritance(strategy = InheritanceType.JOINED)
@DiscriminatorColumn
public abstract class Item extends BaseEntity{
@Id @GeneratedValue
@Column(name="ITEM_ID")
private Long id;
private String name;
private String price;
private int stockQuantity;
@ManyToMany(mappedBy = "items")
private List<Cartegory> cartegories=new ArrayList<>();
}
Album
@Entity
@Getter
@Setter
public class Album extends Item{
private String artist;
private String etc;
}
Book
@Entity
@Getter
@Setter
public class Book extends Item{
private String author;
private String isbn;
}
Movie
@Entity
@Getter
@Setter
public class Movie extends Item{
private String director;
private String actor;
}
이미지 주소

create table Album (
artist varchar(255),
etc varchar(255),
ITEM_ID bigint not null,
primary key (ITEM_ID)
)
Hibernate:
create table Book (
author varchar(255),
isbn varchar(255),
ITEM_ID bigint not null,
primary key (ITEM_ID)
)
Hibernate:
create table Cartegory (
CARTEGORY_ID bigint not null,
createdBy varchar(255),
createdDate timestamp,
lastModifiedBy varchar(255),
lastModifiedDate timestamp,
name varchar(255),
PARENT_ID bigint,
primary key (CARTEGORY_ID)
)
Hibernate:
create table CATEGORY_ITEM (
CATEGOYR_ID bigint not null,
ITEM_ID bigint not null
)
Hibernate:
create table Delivery (
DELIVERY_ID bigint not null,
createdBy varchar(255),
createdDate timestamp,
lastModifiedBy varchar(255),
lastModifiedDate timestamp,
city varchar(255),
status integer,
street varchar(255),
zipcode varchar(255),
primary key (DELIVERY_ID)
)
Hibernate:
create table Item (
DTYPE varchar(31) not null,
ITEM_ID bigint not null,
createdBy varchar(255),
createdDate timestamp,
lastModifiedBy varchar(255),
lastModifiedDate timestamp,
name varchar(255),
price varchar(255),
stockQuantity integer not null,
primary key (ITEM_ID)
)
Hibernate:
create table Member (
MEMBER_ID bigint not null,
createdBy varchar(255),
createdDate timestamp,
lastModifiedBy varchar(255),
lastModifiedDate timestamp,
city varchar(255),
name varchar(255),
street varchar(255),
zipcode varchar(255),
primary key (MEMBER_ID)
)
Hibernate:
create table Movie (
actor varchar(255),
director varchar(255),
ITEM_ID bigint not null,
primary key (ITEM_ID)
)
Hibernate:
create table OrderItem (
ORDER_ITEM_ID bigint not null,
createdBy varchar(255),
createdDate timestamp,
lastModifiedBy varchar(255),
lastModifiedDate timestamp,
count integer not null,
oderPrice integer not null,
ITEM_ID bigint,
ORDER_ID bigint,
primary key (ORDER_ITEM_ID)
)
Hibernate:
create table ORDERS (
ORDER_ID bigint not null,
createdBy varchar(255),
createdDate timestamp,
lastModifiedBy varchar(255),
lastModifiedDate timestamp,
orderDate timestamp,
status varchar(255),
DELIVERY_ID bigint,
MEMBER_ID bigint,
primary key (ORDER_ID)
)

















댓글 ( 4)
댓글 남기기