JPA Entity기본 어노테이션

이동영·2024년 3월 19일

JPA

목록 보기
6/8

Entity란?

JPA에서 엔티티는 데이터베이스에 지속될 수 있는 POJO 즉 순수 객체를 나타낸다. 엔티티는 데이터베이스 테이블을 나타내며 각 인스턴스는 한 행을 나타낸다.

Entity 어노테이션

학생의 데이터를 나타내는 Student라는 POJO가 있고 이를 데이터베이스에 저장하고 싶다고 가정해본다.

public class Student {
    
    // fields, getters and setters
    
}

이를 위해서는 JPA가 인식할 수 있도록 엔티티를 정의해야 한다.

@Entity 어노테이션을 사용하여 정의하며 클래스 수준에서 지정해야 한다.
또한 엔티티에 인자가 없는 생성자 혹은 기본키가 있는지 확인해야 한다.

@Entity
public class Student {
    
    // fields, getters and setters
    
}

엔티티 이름은 기본적으로 클래스의 이름으로 설정된다. name 요소를 사용하여 변경할 수 있다.

@Entity(name="student")
public class Student {
    
    // fields, getters and setters
    
}

@Entity가 붙은 클래스는 JPA 구현체가 각자의 기능을 제공하기 위해 엔티티를 하위 클래스화를 한다. 그렇기에 final키워드를 붙여서는 안된다.

@Id 어노테이션

각각의 JPA엔티티는 유니크한 기본 식별키가 있어야 한다. Id어노테이션으로 기본키를 지정할 수 있다. 여러가지의 방법으로 기본키를 생성할 수 있으며 @GeneratedValue으로 지정할 수 있다.

@GeneratedValue는 strategy요소를 사용하여 네 가지 ID 생성 전략중에서 선택할 수 있으며 값은 AUTO, TABLE, SEQUENCE IDENTITY 네 가지로 설정할 수 있다.

@Entity
public class Student {
    @Id
    @GeneratedValue(strategy=GenerationType.AUTO)
    private Long id;
    
    private String name;
    
    // getters and setters
}

GenerationType.AUTO로 지정한다면 JPA는 식별자를 생성하기 위해 모든 전략을 사용한다. 엔티티 필드 즉 기본키로 지정하는 필드에 어노테이션을 추가한다면 JPA는 지정한 필드를 데이터베이스의 열과 매핑하여 데이터를 관리하게 된다.

필드 접근(Field Access)이외에도, 속성 접근(Property Access)이나 혼합 접근(Mixed Acess)도 가능하다. 이는 필드와 속성 모드를 사용할 수 있도록 해준다.

@Table 어노테이션

대부분의 경우 데이터베이스 테이블의 이름과 엔티티의 이름은 동일하지 않다. 이러한 경우에 @Table을 사용하여 테이블 이름을 지정할 수 있다.

@Entity
@Table(name="STUDENT")
public class Student {
    
    // fields, getters and setters
    
}

스키마 요소를 사용하여 스키마를 언급할 수도 있다.

@Entity
@Table(name="STUDENT", schema="SCHOOL")
public class Student {
    
    // fields, getters and setters
    
}

스키마의 이름은 한 테이블 세트를 다른 테이블 세트와 구별하는 데 도움이 된다.
@Table을 사용하지 않으면 테이블 이름이 엔티티 이름이 된다.

@Column

테이블 어노테이션과 마찬가지로 Column 주석을 사용하여 테이블의 열 세부 정보를 지정할 수 있다. @Column은 이름 길이 null허용여부, 고유값등 여러가지의 속성을 지정할 수 있다.

@Entity
@Table(name="STUDENT")
public class Student {
    @Id
    @GeneratedValue(strategy=GenerationType.AUTO)
    private Long id;
    
    @Column(name="STUDENT_NAME", length=50, nullable=false, unique=false)
    private String name;
    
    // other fields, getters and setters
}

name : 컬럼의 이름을 지정한다.
length : 컬럼의 길이를 지정한다.
nullable : 열이 null을 허용하는지 여부를 지정한다.
unique : 열이 고유한 값으로 저장할 것인지를 지정한다.

@Column을 지정하지 않으면 테이블 컬럼 이름이 필드 이름이 된다.

@Transient

필드를 비영속적으로 만들고 싶을 때 사용하여 필드가 유지 되지 않도록 지정한다.
예를들어 생년월일을 기준으로 학생의 나이를 계산할 수 있다. @Transient를 영령 필드에 달아본다.

@Entity
@Table(name="STUDENT")
public class Student {
    @Id
    @GeneratedValue(strategy=GenerationType.AUTO)
    private Long id;
    
    @Column(name="STUDENT_NAME", length=50, nullable=false)
    private String name;
    
    @Transient
    private Integer age;
    
    // other fields, getters and setters
}

결과적으로 해당 필드는 테이블에 매핑이 되지 않는다.

@Temporal

테이블에 임시의 값을 저장할 때 사용하지만 굳이 이걸 사용할 빠에는 자료구조를 사용한다.

@Entity
@Table(name="STUDENT")
public class Student {
    @Id
    @GeneratedValue(strategy=GenerationType.AUTO)
    private Long id;
    
    @Column(name="STUDENT_NAME", length=50, nullable=false, unique=false)
    private String name;
    
    @Transient
    private Integer age;
    
    @Temporal(TemporalType.DATE)
    private Date birthDate;
    
    // other fields, getters and setters
}

그러나 JPA 3.1에서는 java.time.LocalDate, java.time.LocalTime, java.time.LocalDateTime, java.time.OffsetTime 및 java.time.OffsetDateTime도 지원합니다.

@Enumerated

Java의 열거타입은 Emun을 매핑할 때 사용한다.

public enum Gender {
    MALE, 
    FEMALE
}
@Entity
@Table(name="STUDENT")
public class Student {
    @Id
    @GeneratedValue(strategy=GenerationType.AUTO)
    private Long id;
    
    @Column(name="STUDENT_NAME", length=50, nullable=false, unique=false)
    private String name;
    
    @Transient
    private Integer age;
    
    @Temporal(TemporalType.DATE)
    private Date birthDate;
    
    @Enumerated(EnumType.STRING)
    private Gender gender;
    
    // other fields, getters and setters
}

만약 성별을 enum의 순서로 사용한다면, @Enumerated를 지정하지 않아도 된다. 하지만 Enum의 데이터를 디비에도 유지시키고 싶은 경우 속성을 EnumType.STRING로 맞춰주면 된다. 이렇게 설정한 경우 디비에 Enum의 값이 잘 들어간다.

profile
가치를 제공하는 개발자

0개의 댓글