@Entity : JPA가 관리하는 클래스이다. JPA를 사용해서 테이블과 매핑할 클래스는 @Entity가 필수이다.
주의 : 기본 생성자 필수(파라미터가 없는 public/protected 생성자)
애플리케이션 실행시점에 DDL을 자동으로 생성되도록 할 수 있다. 필요하면 테이블을 다 만들어준다. 데이터베이스 방언에 따라 그게 맞는 적절한 DDL을 생성된다.
다만 생성된 DDL은 개발서버에서만 사용해야 하며, 운영서버에서는 적합하지 않다.
hibernate.hbm2ddl.auto = auto
: 테이블이 있으면 DROP 명령어가 수행되고 이후에 다시 테이블을 새로 생성한다.
create
: 기존 테이블 삭제 후 다시 생성(DROP+CREATE)
hibernate.hbm2ddl.auto = create-drop
: create와 동일하나, 프로젝트 종료할 때 테이블을 삭제한다.(CREATE+DROP)
hibernate.hbm2ddl.auto = update
: 변경분만 반영하며 운영 서버에서는 사용해서는 안된다.
hibernate.hbm2ddl.auto = validate
: 엔티티와 테이블이 정상 매핑되었는지만 확인할 때 사용한다.
방언에 따라서 데이터베이스에 맞게 스키마가 자동으로 생성된다.
개발초기 단계 : create or update 권장
테스트 서버 : update or validate 권장
스테이징과 운영서버 : validate or none 권장
운영장비에서는 절대 create, create-drop, update 사용해서는 안된다.
DDL 생성기능은 자동 생성할 때만 사용, JPA 실행 로직에는 전혀 영향을 주지 않는다.
예시) 1. 회원은 일반 회원과 관리자로 구분
2. 회원 가입일과 수정일이 있어야 한다.
3. 회원을 설명할 수 있는 필드가 있어야 한다. 이 필드는 길이 제한이 없다.
[enum 타입 매핑] : 데이터베이스에는 이넘 타입이 없으나, 객체에 이넘타입을 사용하고 싶을 때, @Enumerated를 사용하면 된다.
[날짜 타입 매핑] : @Temporal
데이터베이스에서는 날짜 타입이 세 가지가 있다.
package javax.persistence;
public enum TemporalType {
DATE, //날짜만
TIME,//시간만
TIMESTAMP;//날짜와 시간 모두
private TemporalType() {
}
}
@Column
@Enumerated
@Temporal
@Lob
@Transient
기본키 매핑방법
package jpabasic;
import javax.persistence.EntityManager;
import javax.persistence.EntityManagerFactory;
import javax.persistence.EntityTransaction;
import javax.persistence.Persistence;
public class Main {
public static void main(String[] args) {
EntityManagerFactory emf = Persistence.createEntityManagerFactory("hello");
EntityManager em = emf.createEntityManager();
EntityTransaction tx = em.getTransaction();
//엔티티 매니저에서 수행하는 모든 로직은 트랜잭션 안에서 수행되어야 한다.
tx.begin();
try{
Member member = new Member();
member.setId("ID_A");
member.setUsername("C");
em.persist(member);
tx.commit();
}catch(Exception e){
tx.rollback();
}finally {
em.close();
}
emf.close();
}
}
직접 할당을 하려는 경우 : @Id만 사용
자동 생성하는 경우 : @GeneratedValue를 사용하면 된다.
GenerationType에는 크게 세 가지다. SEQUENCE, IDENTITY, TABLE(, AUTO(이 셋 중 하나로 선택되는 것))
//
package javax.persistence;
public enum GenerationType {
TABLE,
SEQUENCE,
IDENTITY,
AUTO;
private GenerationType() {
}
}
IDENTITY전략 : DB가 기본 키 생성을 위임받는 것을 말한다.(주로 MySQL을 사용하는 경우 사용한다.)(크게 메리트는 없다.)
INSERT 쿼리문
이 실행되고 그 이후에 트랜잭션 커밋
된다. 영속성 컨텍스트에 그 커밋된 값이 들어가게 된다. DB INSERT하는 시점에 그 상태값을 알고 있기 때문에 select문은 안나간다. em.persist()
가 되고 바로 INSERT 쿼리문 실행 -> 트랜잭션 커밋된다. 따라서 DB에 INSERT문이 들어간 후에야 ID값을 알 수 있다.SEQUENCE전략 : 오라클 db에서 주로 사용한다. 시퀀스 오브젝트를 통해서 값을 생성, 이를 가져와서 객체에 기본 키를 세팅한다. 하이버네이트가 생성하는 기본 시퀀스를 사용한다.
em.persist
가 이뤄진다. (참고) : 기본 키는 Long을 사용하는 것으로 권장된다.
Table 전략 : 키 생성 전용 테이블을 하나 만들어서 데이터베이스 시퀀스를 흉내내는 전략(현업에서는 잘 사용하지 않는다.)
권장하는 식별자 전략
데이터 중심 설계 문제점
@Column(name = "MEMBER_ID")
private Long memberId; // 관계형 DB에 맞춰서 설계
참조가 없어서 객체 그래프 탐색이 불가능하고 테이블 설계에 맞춘 방식이다.