JPA를 사용하는 데 가장 중요한 일은 엔티티와 테이블을 정확히 매핑하는 것이다.
엔티티에서 사용하는 어노테이션에 대해 알아보자.
@Entity 적용 시 주의 사항
- 기본 생성자는 필수다. 없으면 기본적으로 생성해준다.
- 저장할 필드에 final을 사용하면 안된다.
@Enumerated(EnumType.STRING)
- enum을 사용하여 타입을 구분한다. 다음과 같은 어노테이션으로 매핑을 해야 한다.
- STRING 타입을 선택해야 enum 이름을 db에 저장한다. 기본 값은 ORDINAL이다.
@Lob
- 긴 설명을 하는 필드는 길이 제한이 없다. 따라서 db의 VARCHAR 타입 대신 CLOB 타입으로 저장해야 한다.
- @Lob 를 사용하면 CLOB, BLOB 타입을 매핑할 수 있다.
- CLOB : 문자형 대용량 파일 저장하는데 사용 타입 매핑
- BLOB : 이미지, 비디오 등 멀티미디어 데이터 다룰 때 사용
@Temporal
- 날짜 타입을 매핑한다.
- BaseEntity 클래스를 만들어 상속받아 사용하는 것을 추천한다.
@Transient
- 특정 필드를 db에 저장하지 않고 조회하지도 않는다.(매핑을 안한다.)
- 객체에 임시로 어떤 값을 보관하고 싶을 때 사용한다.
@Access
- JPA가 엔티티에 접근하는 방식을 지정한다.
@Column
- 자주 사용되는 속성으로는 name, nullable, unique, length : string 타입에만 사용
데이터베이스 스키마 자동 생성
JPA는 db 스키마를 자동으로 생성하는 기능을 지원한다. DDL을 보면 엔티티와 테이블이 어떻게 매핑되는지 쉽게 이해할 수 있다.
DDL 사용 시 주의 사항
- 운영 서버에서 create, create-drop, update처럼 DDL을 수정하는 옵션은 절대 사용하면 안 된다.
- 개발 환경에서는 추천 전략이 있다.
- 개발 초기 단계는 create 또는 update를 사용한다.
- 테스트 서버는 update 또는 validate 또는 none을 사용한다.
- 스테이징과 운영 서버는 validate 또는 none을 사용한다.
DDL 생성 기능
- 스키마 자동 생성하기를 통해 만들어지는 DDL에 제약조건을 추가해보자
@Table(uniqueConstraints = {@UniqueConstraint(
columnNames = {"Name", "AGE"} )})
...
@Column(name = "Name", nullable = false, length = 10)
private String username;
직접 DDL을 만든다면 사용할 이유가 없지만 이러한 기능을 사용하면 개발자가 엔티티만 보고 다양한 제약조건을 파악할 수 있는 장점이 있다.
기본 키 매핑
@Id 어노테이션을 사용하여 매핑해 준다. MySQL 데이터베이스를 사용한다면 전략으로 IDENTITY를 사용해 자동으로 AUTO_INCREMENT 기능을 적용시킨다. 자동 생성 전략이 다양한 이유는 데이터베이스 벤더마다 지원하는 방식이 다르기 때문이다.
strategy 선택
- PostgreSQL는 주로 IDENTITY 전략 사용
- 오라클은 주로 SEQUENCE 전략 사용
- 선택을 안하면 기본 값으로 AUTO 전략이다.
권장하는 식별자 선택 전략
- null 값 허용하지 않는다.
- 유일해야 하고 변해선 안 된다.
- 자연 키보다는 대리 키를 권장한다. 예를 들면 회원의 전화번호는 없을 수 있고 변경될 수도 있다. 주민등록번호는 null값도 아니고 유일하며 변하지 않아서 만족 할 수 있다.
- 대리 키를 기본 키로 사용하되 주민등록번호나 이메일처럼 지연 키의 후보가 되는 컬럼들은 필요에 따라 유니크 인덱스를 설정해서 사용하는 것을 권장한다.
- 2개 이상의 컬럼으로 기본 키를 구성하는 복합 키 사용도 있다.
엔티티에 비즈니스 로직을 넣어야 한다?
도메인 주도 개발 방법론(DDD - Domain Driven Development)를 참조