
Hibernate(또는 여러 기술 벤더들이 있음@Entity)으로 매핑📂 build.gradle
JDBC 관련 라이브러리를 추가implementation 'org.springframework.boot:spring-boot-starter-data-jpa'
📂 application.properties
show-sql : JPA가 생성하는 SQL을 출력ddl-auto=none : JPA의 테이블 자동 생성 기능을 끔create : 애플리케이션 실행 시 기존 테이블 삭제 후 새로 생성create-drop : 애플리케이션 실행 시 테이블 생성, 종료 시 테이블 삭제update : 데이터베이스 스키마를 매핑 정보와 비교해 필요한 부분만 변경validate : 데이터베이스와 매핑 정보 검증만 수행spring.jpa.show-sql=true
spring.jpa.hibernate.ddl-auto=none
📂 Member
@Entity : 데이터베이스 테이블과 매핑되는 클래스 명시@Id : 기본 키 지정@GeneratedValue(strategy = GenerationType.IDENTITY) : 기본 키 자동 생성 전략GenerationType.IDENTITY : DB의 AUTO_INCREMENT 기능 사용GenerationType.SEQUENCE : DB의 시퀀스를 사용(Oracel, PostgreSQL)GenerationType.TABLE : 별도의 키 관리 테이블 사용GenerationType.AUTO : DB에 맞는 전략을 자동 선택@Entity
public class Member {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
private String name;
public Long getId() {return id;}
public void setId(Long id) {this.id = id;}
public String getName() {return name;}
public void setName(String name) {this.name = name;}
}
📂 JpaMemberRepository
@Transactional 추가EntityManager로 동작EntityManager를 생성EntityManager를 주입받아야 함public class JpaMemberRepository implements MemberRepository{
private final EntityManager em;
public JpaMemberRepository(EntityManager em) {
this.em = em;
}
@Override
public Member save(Member member) {
em.persist(member);
return member;
}
@Override
public Optional<Member> findById(Long id) {
// find(조회할 타입, 식별자(PK))
Member member = em.find(Member.class, id);
return Optional.ofNullable(member);
}
@Override
public Optional<Member> findByName(String name) {
// 📌 PK가 아닌 다른 컬럼으로 조회시 JPQL을 사용
// JPQL은 테이블 대상 쿼리가 아닌 객체(엔티티) 대상 쿼리
// SELECT 의 대상은 엔티티
List<Member> member = em.createQuery("select m from Member m where m.name = :name", Member.class)
.setParameter("name", name)
.getResultList();
return member.stream().findAny();
}
@Override
public List<Member> findAll() {
return em.createQuery("select m from Member m", Member.class).getResultList();
}
}
EntityManager는 내부에 Persistence Context를 둬서 엔티티들을 관리close() 메서드가 호출되면 더 이상 사용❌EntityManager가 관리하는 1차 캐시 역할User user = new User(); // 비영속 (Transient)
em.persist(user); // 영속 (Persistent)
em.detach(user); // 준영속 (Detached)
em.remove(user); // 삭제 (Removed)
persist() 호출 후 관리되는 상태detach() 또는 clear() 호출 시 관리가 해제된 상태remove() 호출 후 삭제 예약 상태EntityManager 인스턴스를 생성하는 팩토리 클래스EntityManagerFactory emf = Persistence.createEntityManagerFactory("example-unit");
EntityManager em1 = emf.createEntityManager(); // EntityManager 생성
EntityManager em2 = emf.createEntityManager(); // 또 다른 EntityManager 생성
em1.close();
em2.close();
emf.close(); // 최종 종료
EntityManagerFactory 생성 : 전체 애플리케이션에서 하나만 생성EntityManager 생성 : 각 작업 단위(트랜잭션)에 대해 생성