해당 시리즈는 김영한님의 JPA 로드맵을 따라 학습하면서 내용을 정리하는 글입니다
JPA
는 특정 데이터베이스에 종속되지 않습니다
각각의 데이터베이스가 제공하는 SQL 문법과 함수는 조금씩 다른다는 문제가 생기게 되겠죠
MySQL
은 VARCHAR
, Oracle
은 VARCHAR2
SUBSTRING()
, Oracle
은 SUBSTR()
MySQL
은 LIMIT
, Oracle
은 ROWNUM
방언: SQL 표준을 지키지 않는 특정 데이터베이스만의 고유한 기능
hibernate.dialect
속성에 지정해서 사용합니다
하이버네이트는 40가지 이상의 데이터베이스 방언을 지원합니다(실무에서 사용되는 DB는 거의 지원된다고 생각하면 됩니다)
Persistence
라는 클래스에서 설정 정보를 읽어서 EntityManagerFactory
라는 클래스를 생성합니다EntityManagerFactory
에서 생성한 EntityManager
를 사용하게 됩니다EntityManagerFactory
는 어플리케이션이 구동되는 시점에 한번만 생성되지만, EntityManager
는 고객의 요청이 올 때마다 생성됩니다EntityManager
는 쓰레드간의 공유를 하면 안됩니다!!@Entity
: JPA
가 관리할 객체@Id
: 데이터베이스 PK
와 매핑JPA
를 통해서 Entity
를 가져오면 해당 Entity
는 JPA
가 관리합니다JPA
는 트랜잭션을 커밋하는 시점에 변경점이 있는지 확인합니다JPA
가 업데이트 쿼리를 작성해주고 커밋을 날리게 됩니다SQL
을 추상화해서 특정 데이터베이스 SQL
에 의존하지 않습니다JPQL
을 한마디로 정의하면 객체 지향 SQL
EntityManager.find()
a.getB().getC()
)EntityManagerFactory emf = Persistence.createEntityManagerFactory("hello");
EntityManager em = emf.createEntityManager();
EntityTransaction tx = em.getTransaction();
tx.begin();
try {
List<Member> result = em.createQuery("select m from Member as m", Member.class)
.getResultList();
Pagination
에서 이점을 볼 수 있습니다 List<Member> result = em.createQuery("select m from Member as m", Member.class)
.setFirstResult(1)
.setMaxResults(10)
.getResultList();
JPQL
을 작성했을 때, DB
에 날아가는 쿼리문은Hibernate:
/* select
m
from
Member as m */ select
member0_.id as id1_0_,
member0_.name as name2_0_
from
Member member0_ limit ? offset ?
limit
와 offset
이 작성되어 날아갑니다DB
마다 페이징 처리하는 방법은 다르기 때문에 JPQL
이 없이 우리가 직접 페이징 처리를 하려면 그 많은 데이터베이스 방언을 외워야 하겠지만 JPQL
을 사용하면 신경쓰지 않아도 됩니다JPA
를 사용하면 엔티티 객체를 중심으로 개발하게 됩니다JOIN
등)DB
데이터를 객체로 변환해서 검색하는 것은 불가능합니다DB
에서 불러오려면 결국 검색 조건이 포함된 SQL
이 필요합니다JPA
는 SQL
을 추상화한 JPQL
이라는 객체 지향 쿼리 언어를 제공합니다SQL
과 문법이 유사하고, SELECT
, FROM
, WHERE
, GROUP BY
, HAVING
, JOIN
을 지원합니다JPQL
은 엔티티 객체를 대상으로 쿼리,SQL
은 데이터베이스 테이블을 대상으로 쿼리를 한다는 차이가 있습니다