[2] JPA 시작

ttt-1-2·2026년 3월 15일

교재: 자바 ORM 표준 JPA 프로그래밍 

깃허브: https://github.com/holyeye/jpabook


2026년 3월 기준으로 책 내용을 변경해서 실습을 진행했다: (1) 이클립스 → 인텔리제이 (2) Maven → Gradle

폴더 구조는 다음과 같다:

build.gradle

  • Gradle: 프로젝트의 의존성과 빌드 설정을 관리하는 파일이다. 어떤 라이브러리를 사용할지, 자바 버전은 무엇인지 등을 여기서 설정한다.
plugins {
    id 'java'
}

group = 'hellojpa'
version = '1.0-SNAPSHOT'

repositories {
    mavenCentral()
}

dependencies {
    implementation 'org.hibernate:hibernate-core:5.6.15.Final'
    implementation 'javax.persistence:javax.persistence-api:2.2'
    runtimeOnly 'com.h2database:h2:2.2.224'
}

java {
    toolchain {
        languageVersion = JavaLanguageVersion.of(17)
    }
}

persistence.xml

persistence.xml은 JPA 설정 파일이다. 사용할 데이터베이스, 사용할 JPA 구현체, 엔티티 클래스, JPA 동작 옵션 등은 여기에서 설정한다.

<?xml version="1.0" encoding="UTF-8"?>
<persistence 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"
             version="2.2">
		
		// persistence-unit은 JPA 설정 단위이다
    <persistence-unit name="jpabook">
				// JPA가 관리할 엔티티 클래스를 등록한다
        <class>hellojpa.Member</class>

        <properties>

            <!-- database connection -->
            <property name="javax.persistence.jdbc.driver" value="org.h2.Driver"/>
            <property name="javax.persistence.jdbc.url" value="jdbc:h2:~/test"/>
            <property name="javax.persistence.jdbc.user" value="sa"/>
            <property name="javax.persistence.jdbc.password" value=""/>

            <!-- Hibernate -->
            <property name="hibernate.dialect" value="org.hibernate.dialect.H2Dialect"/>

            <!-- console SQL -->
            <property name="hibernate.show_sql" value="true"/>
            <property name="hibernate.format_sql" value="true"/>

            <!-- auto create table -->
            <property name="hibernate.hbm2ddl.auto" value="create"/>

        </properties>

    </persistence-unit>

</persistence>

Member

이번 실습에서 Member 클래스는 JPA 엔티티 클래스이다. 데이터베이스 테이블과 매핑된다.

package hellojpa;

import javax.persistence.*;
import lombok.Getter;
import lombok.Setter;

@Entity
@Table(name = "MEMBER")
@Getter
@Setter

public class Member {

    @Id
    @Column(name = "ID")
    private String id;

    @Column(name = "NAME")
    private String username;

    // 매핑 정보가 없는 필드
    private Integer age;
}
  • @Entity: 이 클래스가 JPA 엔티티임을 나타낸다 → 이 객체는 데이터베이스 테이블과 매핑된다
  • @Table: 엔티티가 매핑될 테이블 이름을 지정한다
  • @Id: 기본 키를 지정한다
  • @Column: 필드와 DB 컬럼을 매핑한다
  • 매핑 어노테이션이 없으면 필드 이름 그대로 컬럼이 생성된다

참고: JPA 어노테이션의 패키지는 javax.persistence이다.

JpaMain

  • EntityManagerFactory: EntityManager를 생성한다. 애플리케이션 전체에서 하나만 생성한다.
  • EntityManager: JPA의 핵심 객체이다. (엔티티 저장, 엔티티 조회, 엔티티 수정, 엔티티 삭제)
  • 트랜잭션: JPA의 모든 데이터 변경 작업은 트랜잭션 안에서 실행해야 한다.
package hellojpa;

import javax.persistence.*;
import java.util.List;

public class JpaMain {
    public static void main(String[] args) {

        // 엔티티 매니저 팩토리 - 생성
        EntityManagerFactory emf = Persistence.createEntityManagerFactory("jpabook");

        // 엔티티 매니저 - 생성
        EntityManager em = emf.createEntityManager();

        // 트랜잭션 - 획득
        EntityTransaction tx = em.getTransaction();

        try {
            tx.begin();
            logic(em);
            tx.commit();
        } catch (Exception e) {
            tx.rollback();
        } finally {
            em.close();
        }
        emf.close();
    }

    // 비지니스 로직
    private static void logic(EntityManager em) {
        String id = "id1";
        Member member = new Member();
        member.setId(id);
        member.setUsername("유정");
        member.setAge(2);

        // 등록
        em.persist(member);
        // 수정
        member.setAge(20);
        // 한 건 조회
        Member findMember = em.find(Member.class, id);
        System.out.println("findMember=" + findMember.getUsername() + ", age=" + findMember.getAge());
        // 목록 조회
        List<Member> members = em.createQuery("select m from Member m", Member.class).getResultList();
        System.out.println("members.size=" + members.size());

        // 삭제
        em.remove(member);
    }
}

0개의 댓글