프로젝트/기술적 선택

[기술적 선택] JPA 선택 이유

배발자 2022. 12. 27.
반응형

개요

필자는 올해 상반기 JPA를 활용한 프로젝트를 진행한 바 있다. 하지만 가장 중요한 점은 어떻게 동작하는지에 대한 확실한 개념없이 프로젝트를 진행했던 터라 JPA 에 대해 자세히 물어보면 죄송합니다부터 나올 거라고 생각한다. 최근 네이버, 카카오 같은 IT 기업에서 면접을 보고 느꼈던 것은 "왜 이 기술을 사용했는지, 어떻게 동작하는지"에 대해 깊게 생각하고 고민하고 파고드는 개발자를 원한다는 것을 간접적으로 뼈저리게 느꼈다. 그래서 오늘은 JPA를 대체 왜 쓰는가부터 천천히 정리해 볼 생각이다. 

 

SQL 의 문제점 

보통 프로젝트를 진행하면 스프링과 데이터베이스와 연동을 하면서 서로 데이터를 넣고 받는 역할을 많이 한다. 그렇다면 데이터베이스의 데이터를 얻기 위해서는 수많은 쿼리문들을 개발자들이 짜야하고 복잡하고 힘든 노동의 시간들이 돌아올 것이다. 또한, 객체는 추상화, 상속, 다형성 같은 객체 지향적 특징을 가지고 있는 반면, 관계형 데이터베이스는 단순히 데이터 중심으로 이뤄져있다. 즉, RDB에 객체를 저장하는 데 패러다임의 불일치가 발생한다. 

 

1. 상속

객체랑 다르게 테이블은 상속이라는 기능이 없다. 개발자가 조인문, 삽입문 등 여러 쿼리를 생성해야한다. 

 

2. 연관 관계

객체는 참조를 사용해서 연관된 객체를 조회하는데, 테이블은 외래키로 연관관계를 설정하고 조인으로 연관 테이블을 조회한다. 

 

3. 객체 그래프 탐색

객체는 자유롭게 객체 그래프를 탐색할 수 있어야 하지만 SQL을 이용해 조회를 했다면 실행된 처음 SQL에 따라 탐색의 범위가 저장되기 때문에 제약이 발생한다. 따라서 DAO를 통해 실행된 SQL 을 직접 확인해야만 탐색이 가능하다. 

 

4. 비교

DB는 기본키로 각 행을 구분한다. 스프링 환경에서 동일한 기본키를 가진 행을 가져와서 동일성을 비교한다면 서로 다른 인스턴스로 생성되었기 때문에 동일하지 않다고 나온다. 

 

이러한 문제점들을 JPA 를 사용하여 해결 할 수 있다. 

 

JPA 란

JPA란 Java Persistence API의 약자로써 자바 어플리케이션에서 관계형 데이터 베이스를 사용하는 방식을 정의한 인터페이스이며 자바의 ORM 기술 표준이다. 

 

ORM 기술이라는 것이 도대체 무슨 말인가? 

 

쉽게 설명하자면 Spring 에서 생성한 객체 인스턴스의 데이터들을 특정 테이블에 넣고 싶을 때 보통 이 데이터가 저 테이블의 특정 컬럼에 매핑 하고 이거 하나하나를 직접 쿼리문을 작성을 했어야했다. 하지만, 객체는 객체대로 생성을 하고 RDB에서는 RDB대로 설계를 하고나서 해당 테이블의 정보 컬럼들을 가지고 있는 스프링 객체가 있다면 ORM 이 SQL을 자동 생성해서 해결해준다. 즉, 객체와 RDB 를 매핑해주는 기술이다. 

 

 

 

JPA는 애플리케이션과 JDBC 사이에서 동작한다. JPA 내부에서 JDBC API를 사용하여 SQL을 호출하여 DB와 통신한다.

개발자가 ORM 프레임워크에 저장하면 적절한 INSERT SQL을 생성해 데이터베이스에 저장해주고, 검색을 하면 적절한 SELECT SQL을 생성해 결과를 객체에 매핑하고 전달해 준다.

 

JPA 사용 이유 

1. 생산성 증가

DDL 을 자동으로 생성을 해주기 때문에 생산성이 증가한다. 스프링 환경에서 간단한 메서드로 CRUD 가 가능해진다. 

 

2. 유지보수가 쉽다.

만약 테이블 컬럼명을 바꿔야 할 경우 SQL일 경우 기존에 작성되었던 모든 쿼리문을 변경해야하지만 JPA 를 활용하면 

매핑 정보만 변경하면 쉽게 해결된다. 

 

3. 패러다임 불일치 해결

JPA 는 연관된 객체를 사용하는 시점에 SQL 을 전달할 수 있고, 같은 트랜잭션 내에서 조회할 때 동일성 보장해준다. 

 

4. 성능 

같은 트랜잭션 안에서는 같은 엔티티를 반환하여 데이터 베이스와의 통신 횟수를 줄인다. (1차 캐쉬, 쓰기 지연 SQL 저장소) 

 

Hibernate

JPA 는 기술에 대한 API 표준 명세라고 소개하였다. 즉, JPA 는 특정 기능을 하는 라이브러리가 아니고, ORM을 사용하기 위해 인터페이스를 모아둔 것이라고 보면 된다. 인터페이스로 정의되어 있기 때문에 구현이 없다. JPA 를 정의한 javax.persistence 패키지의 대부분은 inteface, enum, Exception, Annotation 들로 이루어져있다. 추후 JPA의 핵심인 EntityManager 라는 것을 배울텐데 Javax.persistence 패키지 안에 integerface로 정의되어 있다. 

 

package javax.persistence;
 
import ...
 
public interface EntityManager {
 
    public void persist(Object entity);
 
    public <T> T merge(T entity);
 
    public void remove(Object entity);
 
    public <T> T find(Class<T> entityClass, Object primaryKey);
 
    // More interface methods...
}

[EntityManager]

 

 

그렇다면 어떻게 JPA를 활용을 해야할까? 생각을 해보면 껍데기만 있는 인터페이스를 사용하기 위해 자바 개발자들은 구현체를 만들어서 사용한다. JPA도 이와 같다. 껍데기를 채워놓아야 할 그 놈이 Hibernate 이다. 

 

 

 

 

Hibernate 는 JPA 의 구현체 중 하나이며 자바 언어를 위한 ORM 프레임워크이다. 위의 그림을 보면 Hibernate, EclipseLink, DataNucleus 가 JPA 의 구현체라고 보면 된다. 필자는 Hibernate 를 활용한 프로젝트를 준비하고 있기 때문에 JPA 관련 기술들은 모두 Hibernate를 사용한다고 보면 된다. 

 

SQL mapper와의 차이

필자는 마이바티스를 활용하여 작은 프로젝트를 해본 경험이 있다. 마이바티스는 SQL mapper를 활용하여 직접 DB와 객체를 매핑하기 위해 SQL 쿼리문을 작성해야 했다. 마이바티스를 모르는 사람들에게 간단하게 설명하자면, XML 파일에 직접 SQL를 작성해야 한다. 즉, 쿼리를 코드 단에 그대로 작성하므로 보안/유지보수가 미흡하다는 것이다. 

 

그러나 하이버네이트 같은 ORM 프레임워크의 경우, 직접 쿼리를 작성하지 않고 JPA로 명세된 테이블 정보를 이용해 객체와 DB를 매핑시킨다. 즉, 코드에 직접 쿼리를 작성할 필요가 없다. 

 

 

Spring Boot 호환 확인하는 법

 

Spring Boot

Commercial support Business support from Spring experts during the OSS timeline, plus extended support after OSS End-Of-Life. Publicly available releases for critical bugfixes and security issues when requested by customers.

spring.io

 

자신이 진행하고 하는 스프링 부트 버전 들어간다. 

 

 

 

Reference Doc 클릭 -> pdf 클릭  -> org.hibernate 검색

 

 

 

hibernate.orm 버전 확인 

 

스프링 부트 3.0.1 버전은 hibernate 6.1.6 과 호환 

 

 

 

 

반응형

댓글