JPA

@MappedSuperclass 어노테이션

방구석 대학생 2020. 10. 10. 23:19

"인프런 - 자바 ORM 표준 JPA 프로그래밍 강의를 듣고 작성한 글 입니다."

www.inflearn.com/course/ORM-JPA-Basic#

 

자바 ORM 표준 JPA 프로그래밍 - 기본편 - 인프런

JPA를 처음 접하거나, 실무에서 JPA를 사용하지만 기본 이론이 부족하신 분들이 JPA의 기본 이론을 탄탄하게 학습해서 초보자도 실무에서 자신있게 JPA를 사용할 수 있습니다. 초급 웹 개발 프로그

www.inflearn.com

 

이번 글에서 얘기할 @MappedSuperclass 어노테이션은 상속관계 매핑과는 큰 상관이 없다.

이 어노테이션은 진짜 단순하게 객체 입장에서 서로 다른 여러개의 클래스에서 똑같은 필드가 계속 나올 때 해당 필드들을 부모 클래스에 두고 속성만 상속해서 사용하고 싶은 경우, 즉 공통 매핑 정보가 필요할 때 사용하는 어노테이션이다.(즉, 귀찮음을 좀 줄일 때 쓰는 것)

 

예시 : 항상 모든 테이블에 동일한 정보가 들어가 있어야 하는 경우 어떻게 해야 할까?

-> BaseEntity 클래스를 생성하고 그 안에 아래의 코드와 Getter, Setter 를 만들어준 후, @MappedSuperclass 어노테이션을 선언해준 다음 Member, Team 클래스에 extends 키워드로 BaseEntity 를 슈퍼클래스로 상속받아 주자.

 

- BaseEntity.java

@MappedSuperclass // 매핑 정보만 받는 슈퍼 클래스임을 명시한다.
public class BaseEntity {

	private String createdBy;
	private LocalDateTime createdDate;
	private String lastModifiedBy;
	private LocalDateTime lastModifiedDate;

	// Getter, Setter
}

 

- Member.java

@Entity
public class Member extends BaseEntity{
	.......
}

 

- Team.java

@Entity
public class Team extends BaseEntity{
	.....
}

 

위와 같이 코드를 작성해 준 후 JpaMain 클래스에 아래와 같은 코드를 작성한 후 애플리케이션을 실행해보자.

(BaseEntity 클래스의 경우 각 필드들에 @Column 어노테이션의 name 속성을 이용하여 이름을 바꿔주는 것도 가능하다.)

 

애플리케이션을 실행 할 경우 아래와 같은 hibernate SQL 을 출력하는 것을 볼 수 있다.

(BaseEntity 는 매핑 정보만 받는 슈퍼 클래스 이기 때문에 따로 테이블이 생기지 않는다. - Entity 가 아니므로 테이블과 매핑되지 않는다.)

- hibernate SQL

Hibernate: 
    
    create table Member (
       MEMBER_ID bigint not null,
        createdBy varchar(255),
        createdDate timestamp,
        lastModifiedBy varchar(255),
        lastModifiedDate timestamp,
        USERNAME varchar(255),
        LOCKER_ID bigint,
        TEAM_ID bigint,
        primary key (MEMBER_ID)
    )
Hibernate: 
    
    create table Team (
       TEAM_ID bigint not null,
        createdBy varchar(255),
        createdDate timestamp,
        lastModifiedBy varchar(255),
        lastModifiedDate timestamp,
        name varchar(255),
        primary key (TEAM_ID)
    )

 

위의 SQL 문을 잘 보면 BaseEntity 클래스에 선언해 놓은 필드들이 Member, Team 테이블에 모두 상속 되었으며, 그로 인해 해당 필드들과 메소드들을 모두 상속 받아서 쓸 수 있는 것을 볼 수 있다.

 

@MappedSuperclass 어노테이션이 선언된 클래스는 부모 클래스를 상속 받는 자식 클래스에 매핑 정보만 제공하며

조회, 검색이 불가능하다.(em.find(BaseEntity) 같은 작업이 불가능하다.)

직접 생성해서 사용할 일이 없으므로 추상 클래스로 생성할 것을 권장한다.