작성 예시 코드
@Entity // JPA가 관리할 수 있는 Entity 클래스 지정
@Table(name = "memo") // 매핑할 테이블의 이름을 지정
public class Memo {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
// nullable: null 허용 여부
// unique: 중복 허용 여부 (false 일때 중복 허용)
@Column(name = "username", nullable = false, unique = true)
private String username;
// length: 컬럼 길이 지정
@Column(name = "contents", nullable = false, length = 500)
private String contents;
}
@Entity
: JPA가 관리할 수 있는 Entity 클래스로 지정@Entity(name = "Memo")
" Entity 클래스의 이름을 지정@Table
: 매핑할 테이블 지정@Column
: 테이블의 컬럼을 지정 (default:객체의 필드명)@Column(name = "username")
: 테이블의 컬럼과 객체의 필드명 설정 (default:객체의 필드명)@Column(nullabel = false)
: 데이터의 null 값 허용 여부 지정 (default: true)@Column(unique = true)
: 데이터의 중복 값 허용 여부 지정 (default : false)@Cloumn(length = 500)
: 데이터 값(문자)의 길이에 제약조건 생성 (default: 255)@Id
: 테이블의 기본 키 지정@GeneratedValue(strategy = GenerationType.IDENTITY)
: 기본 키 생성을 DB에 위임 가능Entity 객체를 효율적으로 쉽게 관리하기 위해 만들어진 공간
JPA는 영속성 컨텍스트에 Entity객체들을 저장하여 관리하면서 DB와 소통한다.
<파일예시>
<?xml version="1.0" encoding="UTF-8"?>
<persistence version="2.2"
xmlns="http://xmlns.jcp.org/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/persistence http://xmlns.jcp.org/xml/ns/persistence/persistence_2_2.xsd">
<persistence-unit name="memo">
<class>com.sparta.entity.Memo</class>
<properties>
<property name="jakarta.persistence.jdbc.driver" value="com.mysql.cj.jdbc.Driver"/>
<property name="jakarta.persistence.jdbc.user" value="root"/>
<property name="jakarta.persistence.jdbc.password" value="{비밀번호}"/>
<property name="jakarta.persistence.jdbc.url" value="jdbc:mysql://localhost:3306/memo"/>
<property name="hibernate.hbm2ddl.auto" value="create" />
<property name="hibernate.show_sql" value="true"/>
<property name="hibernate.format_sql" value="true"/>
<property name="hibernate.use_sql_comments" value="true"/>
</properties>
</persistence-unit>
</persistence>
`EntityManagerFactory emf = Persistence.createEntityManagerFactory("memo")` :
EntityManager em = emf.createEntityManager();
EntityManagerFactory emf = Persistence.createEntityManagerFactory("memo") :
JPA는 persistence.xml 의 정보를 토대로 EntityManagerFactory를 생성
EntityManager em = emf.createEntityManager()
: 코드를 호출하면 EntityManagerFactory를 사용하여 EntityManager를 생성
<SQL에서의 트랜잭션 사용>
START TRANSACTION; # 트랜잭션을 시작합니다.
INSERT INTO memo (id, username, contents) VALUES (1, 'Robbie', 'Robbie Memo');
INSERT INTO memo (id, username, contents) VALUES (2, 'Robbert', 'Robbert Memo');
SELECT * FROM memo;
COMMIT; # 트랜잭션을 커밋합니다.
SELECT * FROM memo;
영속성 컨텍스트로 관리하고 있는 변경이 발생한 객체들의 정보를 쓰기 지연 저장소에 전부 가지고 있다가 마지막에 SQL을 한번에 DB에 요청해 변경을 반영한다.
<코드 예제>
@Test
@DisplayName("EntityTransaction 성공 테스트")
void test1() {
EntityTransaction et = em.getTransaction(); // EntityManager 에서 EntityTransaction 을 가져옵니다.
et.begin(); // 트랜잭션을 시작합니다.
try { // DB 작업을 수행합니다.
Memo memo = new Memo(); // 저장할 Entity 객체를 생성합니다.
memo.setId(1L); // 식별자 값을 넣어줍니다.
memo.setUsername("Robbie");
memo.setContents("영속성 컨텍스트와 트랜잭션 이해하기");
em.persist(memo); // EntityManager 사용하여 memo 객체를 영속성 컨텍스트에 저장합니다.
et.commit(); // 오류가 발생하지 않고 정상적으로 수행되었다면 commit 을 호출합니다.
// commit 이 호출되면서 DB 에 수행한 DB 작업들이 반영됩니다.
} catch (Exception ex) {
ex.printStackTrace();
et.rollback(); // DB 작업 중 오류 발생 시 rollback 을 호출합니다.
} finally {
em.close(); // 사용한 EntityManager 를 종료합니다.
}
emf.close(); // 사용한 EntityManagerFactory 를 종료합니다.
}
EntityTransaction et = em.getTransaction();
: EntityTransaction을 가져와 트랜잭션을 관리et.begin()
: 트랜잭션 시작 명령어et.commit()
: 트랜잭션의 작업을 DB에 반영et.rollback()
: 오류가 발생했을 때, 트랜잭션 작업 취소 후 이전상태로 되돌리는 명령em.persist(memo)
<저장 코드 예시>
@Test
@DisplayName("1차 캐시 : Entity 저장")
void test1() {
EntityTransaction et = em.getTransaction();
et.begin();
try {
Memo memo = new Memo();
memo.setId(1L);
memo.setUsername("Robbie");
memo.setContents("1차 캐시 Entity 저장");
em.persist(memo);
et.commit();
} catch (Exception ex) {
ex.printStackTrace();
et.rollback();
} finally {
em.close();
}
emf.close();
}
em.find(Memo.class, 1)
<조회 코드 예시>
@Test
@DisplayName("Entity 조회 : 캐시 저장소에 해당하는 Id가 존재하는 경우")
void test3() {
try {
Memo memo1 = em.find(Memo.class, 1);
System.out.println("memo1 조회 후 캐시 저장소에 저장\n");
Memo memo2 = em.find(Memo.class, 1);
System.out.println("memo2.getId() = " + memo2.getId());
System.out.println("memo2.getUsername() = " + memo2.getUsername());
System.out.println("memo2.getContents() = " + memo2.getContents());
} catch (Exception ex) {
ex.printStackTrace();
} finally {
em.close();
}
emf.close();
}
em.remove(memo)
<삭제 코드 예시>
@Test
@DisplayName("Entity 삭제")
void test5() {
EntityTransaction et = em.getTransaction();
et.begin();
try {
Memo memo = em.find(Memo.class, 2);
em.remove(memo);
et.commit();
} catch (Exception ex) {
ex.printStackTrace();
et.rollback();
} finally {
em.close();
}
emf.close();
}