JPA는 DB에 쿼리를 자동적으로 DB방언에 맞춰서 만들어 주는 매우 편리한 기능을 제공한다. 그렇기 때문에, 개발자들은, 서비스 로직에 대한 부분에 집중을 할 수 있으며, 반복적인 코드에 대한 소비를 줄 일 수 있다.
이러한 JPA와 객체를 매핑시키는 작업을 어노테이션으로 간단하게 할 수 있다.
1. 엔티티 매핑에 대해서 소개(Entity Mapping)
@Entity
@Entity
public class Member {
private Long id;
private String username;
}
→ 이 엔티티(테이블)는 JPA가 직접 관리한다라는 의미로 밑에 있는 id, username의 객체와 테이블이 매핑된 것이다. 즉, Member class는 JPA가 관리하는 Entity다.
※ 필수 조건으로 반드시 기본 생성자가 존재해야 된다. 또한, final, enum, interface, inner클래스에서 사용할 수없다.
@Entity(name = " ")
name =""를 사용하면 JPA에서 사용할 Entity 이름을 지정할 수 있지만, 기본값이 클래스 이름 그대로이기 때문에, 가급적 기본값으로 사용을 한다.
2. 데이터베이스 스키마 자동 생성(Database Schema)
@Entity
public class Member {
private Long id;
private String username;
private String address; //새로 추가update
prvate String age; // 매핑이 되었는지 확인 validate
}
<properties>
<property name="hibernate.dialect" value="org.hibernate.dialect.H2Dialect"/>
<property name="hibernate.hbm2ddl.auto" value="?" />
</properties>
persistence.xml에서 h2데이터베이스로 데이터 베이스 방언을 설정하고, hibernate가 데이터 베이스 방언으로 적절한 스키마를 생성해준다라는 의미이다.
value="org.hibernate.dialect.(H2 Dialect)에서 (?) 안을 다른 데이터베이스로 설정할 수 있다.
property name="hibernate.hbm2ddl.auto" value="?"의 value안에 create, create-drop , update, validate, none를 넣어 스키마를 자동생성 방식을 정할 수 있다.
- create의 경우기존 테이블을 삭제 후 다시 생성해 준다. 즉, 애플리케이션을 재가동시 전에 저장되었던, 모든 테이블이 드롭(삭제)되고, 다시 생성되므로 id값이 1부터 시작된다.
- create-drop의 경우 create와 같으나, 종료 시점에 테이블을 drop(삭제)한다.
- update의 경우 변경되는 부분만 반영된다. 위의 Entity 테이블을 보면, address가 새로 추가하고 싶은데, 테이블을 드롭(삭제)하고 싶지 않을 경우 사용한다. (삭제로 인한 update는 불가)
- validate의 경우는 Entity와 테이블이 정상 맵핑 되어 있는지 확인해 준다. age를 추가했는데, 테이블에 정상적으로 들어가 있는지 확인할 때
- none는 뜻그대로, 사용하지 않는다라는 의미이다.
※ 하지만, 운영단계에서 운영서버에서는 절대로 create, create-drop, update를 사용하면 안 된다. 몇천만명의 유저 정보가 있는 테이블이 drop 되고, update로 인해 몇 분간 서비스(시스템)가 중단된다고 생각해보자. 해결할 때 까지 죽어보자..
3. 필드와 칼럼 매핑
@Entity
public class Member {
@Id
private Long id;
@Column(name = "name")
private String username;
private Integer age;
@Enumerated(EnumType.STRING)
private RoleType roleType;
@Temporal(TemporalType.TIMESTAMP)
private Date createdDate;
@Temporal(TemporalType.TIMESTAMP)
private Date lastModifiedDate;
@Lob
private String description;
pubilc Member(){
} //@Entity로 인한 기본생성자 -> @Nooargsconstructor으로 대체 가능
}
(1) @id = id임을 알려준다
(2) @Column(name, nullable, length 등등) = 칼럼의 이름, null값 허용 조건, 문자 길이 제약조건 등을 지정할 수 있다.
(3) @Enumerated(EnumType.STRING) = enum값 매핑을 할 때 사용한다. 속성의 기본값이 ORDINAL로 되어 있지만, STRING으로 바꾸어 줘야 한다. 그 이유는, 데이터 베이스에 보면, roleType이 숫자로 들어와 있기 때문이다.
username1의 RoleType(RoleType.USER) -> 데이터베이스에 RoleType = 0으로 저장된다.
username2의 RoleType(RoleType.ADMIN) -> 데이터베이스에 RoleType= 1으로 저장된다.
하지만, 여기에 GUEST라는 RoleType가 추가된다면
밑에 예제를 보자
public enum RoleType{
USER, ADMIN // -> STUDENT가 추가
STUDENT, USER, ADMIN
}
STUDENT의 추가로
username1의 RoleType(RoleType.USER) -> 데이터베이스에 RoleType = 0
username2의 RoleType(RoleType.ADMIN) -> 데이터베이스에 RoleType = 1
username3의 RoleType(RoleType.STUDENT) -> 데이터베이스에 RoleType = 0
으로 010 다시 0부터 시작한다. 예를 들어 0부터 시작하여 1, 2, 3, 4, 5, 6~... 14576849에서 -> 0으로 다시 시작되면 해결할 때까지 죽어야되는 버그가 발생하기 때문에, 꼭 STRING으로 하자 Stirng으로 한다면, USER, ADMIN, STUDENT로 데이터베이스에 저장된다.
(4) @Temporal = TemporalType.DATE: 날짜, 데이터베이스 date 타입과 매핑 (예: 2022–04–22)
TemporalType.TIME: 시간, 데이터베이스 time 타입과 매핑 (예: 12:48:44)
TemporalType.TIMESTAMP: 날짜와 시간, timestamp 타입과 매핑(예: 2022–04–22 12:48:44)
날짜, 시간을 나타낼 수 있다.
(5) @Lob = 지정할 수 있는 속성이 없다. 엄청 큰 데이터를 넣을 때 사용된다.
(6) @Transient = 매핑을 하고 싶지 않을 때 사용된다. 데이터베이스에 저장되지 않는다.
※ 많이 부족한 초보 개발자 입니다. 혼내주세요 배우겠습니다.
'Back-end > Spring' 카테고리의 다른 글
@NoArgsConstructor,@RequiredArgsConstructor,@AllArgsConstructor (0) | 2021.09.11 |
---|---|
@Builder (0) | 2021.09.08 |
@Getter, @Setter (0) | 2021.09.07 |