JPA를 공부, 사용하면서 생기는 어노테이션에 대해 정리한 포스트입니다.
따라서, 수정이 계속 이루어질 수 있는 포스트입니다.
JPA를 사용해 테이블과 일대일 매핑할 클래스에 붙여주는 어노테이션이다. 이 어노테이션을 붙임으로써 JPA가 해당 클래스를 관리하게 된다.
SpringBoot를 설정할 시 spring.jpa.hibernate.ddl-auto 설정이 create or update로 설정할 경우 프로젝트 시작 시 EntityManager가 자동으로 DDL을 수행해준다.
| 속성 | 기능 | 기본값 |
|---|---|---|
| name | JPA에서 사용할 엔티티 이름 지정 | 클래스 이름을 엔티티 이름으로 지정 |
엔티티와 매핑할 테이블을 지정해주는 어노테이션이다.
| 속성 | 기능 | 기본값 |
|---|---|---|
| name | 매핑할 테이블 이름 | 엔티티 이름(@Entity(name="~") 사용 |
| uniqueContraints | DDL 생성시 유니크 제약조건 생성 |
객체 필드를 테이블 컬럼과 매핑한다.
| 속성 | 기능 | 기본값 |
|---|---|---|
| name | 필드와 매핑할 테이블의 컬럼 이름 지정 | 필드이름으로 대체 |
| insertable | Entity 저장 시 해당 Field도 저장, false로 읽기 전용 설정 가능 | true |
| updatable | Entity 수정 시 해당 Field도 수정, false로 읽기 전용 설정 가능 | true |
| table | 하나의 엔티티를 두 개 이상의 테이블에 매핑할 때 사용 | 현재 Class가 매핑된 Table |
| nullable | true/false로 null 허용 여부 설정 | true |
| unique | 컬럼에 유니크 제약조건 부여 | true |
| length | 문자 길이 제약조건 String 타입일 때 사용 | 255 |
| columnDefinition | 데이터베이스 컬럼 정보를 직접 부여 | 적절한 Column Type 생성 |
| precision, scale | BigDecimal 타입에서 사용, precision : 소수점을 포함한 전체 자릿수 설정, scale : 소수의 자릿수 |
-> 여기서 name, insertable, updatable, table을 제외한 나머지 속성들은 DDL 생성 기능을 사용할 때만 사용되는 속성들이다. 즉 실행 로직에는 영향을 끼치지 않는다.
특정 속성을 PK로 설정하는 어노테이션이다.
@Id 어노테이션만 적게될 경우 기본키값을 직접 부여해줘야 한다.@GeneratedValue 어노테이션을 사용하면 기본값을 DB에서 자동으로 생성하는 전략을 사용 할 수 있다.
전략에는 IDENEITY, SEQUENCE, TABLE 3가지가 있다.
IDENTITY : 기본 키 생성을 데이터베이스에 위임한다.(ex MySQL - AUTO INCREMENT...)
SEQUENCE : 데이터베이스 시퀀스를 사용해서 기본 키를 할당한다.(ex Oracle sequence...)
TABLE : 키 생성 테이블을 사용한다.(ex 시퀀스용 테이블을 생성해서 테이블의 기본키를 저장하고 관리한다.)
※ @GeneratedValue(startegy = GenerationType.AUTO) 인 경우 선택된 DB에 따라 JPA가 자동으로 전략 선택
2개 이상의 키를 가지는 복합키로 테이블을 매칭하는 경우 사용하는 어노테이션이다.
@EmbeddedId 어노테이션을 붙여줘야 한다.enum 타입을 매핑할 때 사용한다.
속성 value
EnumType.ORDINAL : enum 순서를 DB에 저장 EnumType.STRING : enum이름을 DB에 저장⭐️ 대부분 경우 STRING을 무조건 사용하는 것이 오류를 줄일 수 있다.
Why? 만약 2개를 저장해둔 enum이 있다고 가정하자. 이 경우를 ORDINAL 속성으로 두면 추후 enum에 1개를 추가할 경우 순서가 밀려 DB의 값들이 깨져서 심각한 오류를 발생할 가능성이 높다. 따라서 STRING으로 저장해두는 것이 안전하다.
어노테이션을 붙인 필드는 DB에 저장하지도 조회하지도 않는다. 객체에 임시로 값을 보관하고 싶을 때 사용
@JoinColumn(name="")
외래키를 정의하는 어노테이션이다.
| 속성 | 기능 | 기본값 |
|---|---|---|
| name | 매핑할 외래키 이름 | '필드명'_'참조하는 테이블 기본키 컬럼명' |
| referencedColumnName | 외래키가 참조하는 대상 테이블의 컬럼명 | 참조하는 테이블 기본키 컬럼명 |
| foreignKey | 외래 키 제약조건 지정 |
@XXToXX
N:1 관계를 표현하는 어노테이션이다. @ManyToOne이 붙은 엔티티가 M이고 반대 엔티티가 1일 때 붙인다.
| 속성 | 기능 | 기본값 |
|---|---|---|
| optional | false : 연관된 엔티티가 항상 존재 | true |
| fetch | 글로벌 페치 전략 설정 | @XXToOne=FetchType.EAGER @XXToMany=FetchType.LAZY |
| cascade | 영속성 전이 기능 사용 | |
| targetEntity | 연관된 엔티티 타입 정보 설정 |
속성으로 mappedBy가 사용, mapppedBy는 양방향 매핑일 때 사용한다.
속성 값에는 반대쪽 매핑의 필드 이름값을 넣는다.
-> 반대쪽 클래스 명으로 매핑 필드값을 정하면 될텐데 왜 mappedBy를 이용해야하는 것인가?
∵ 객체는 서로 다른 단방향 2개로 이루어져있는것과 관련이 있다.
그러면, 2개의 연관관계 ID가 필요하게 된다. 즉, 외래키 2개를 관리하게 될텐데 관계형 데이터베이스는 외래키 1개를 가지고 관리한다.
그래서 JPA는 두 개의 연관관계중 하나를 고르게 하기 위해 mappedBy를 설정한다. 여기서 관리되는 연관관계를 연관관계의 주인이라 한다. 다시 말해 mappedBy가 없는 엔티티가 연관관계의 주인이다.