이 포스트는 인프런 김영한님의 '자바 ORM 표준 JPA 프로그래밍 - 기본편'의 내용을 정리한 포스트 입니다.
여러가지 형태의 데이터베이스가 있지만 주로 사용되는 데이터베이스는 관계형 데이터 베이스이다. 관계형 데이터베이스에서 데이터를 추가하고, 수정하고, 조회하고 삭제하는 과정에서 반복적인 SQL문을 작성해야하는 번거로움이 있는데 이런 과정은 전부 개발자의 몫이다. 또한 SQL을 작성하는 과정에서 발생할 수도 있는 오타에 의한 오류를 수정하는 것도 굉장히 리소스가 많이 필요하다.
우리는 객체의 세상속에서 살고 있다. 따라서 주로 사용하는 언어도 객체 지향적인 언어이다. 하지만 데이터를 저장하고 관리하기 위해 관계형 데이터베이스를 사용한다. 바로 이 부분에서 패러다임의 불일치가 발생한다.
구체적인 예로 연관관계에 있는 두 객체를 객체 세상에서 다루는 것과 관계형 데이터베이스 세상에서 다루는 것에 아주 큰 차이가 있다. 객체는 연관관계를 다루기 위해 참조를 사용하는데 테이블은 외래 키를 사용한다. 이런 불일치를 해결하기 위해 객체의 속성값으로 외래 키를 저장하는 방식을 생각해볼 수 있지만 이런 방식은 객체지향적이지 않다.
또한 객체 세상에서는 자바 컬렉션에 add()
를 사용해서 저장할 수가 있지만 관계형 DB세상에서는 값들을 하나씩 다 넣어준 다음 insert
를 활용해서 값을 저장해야하는 불일치가 발생한다.
객체그래프 탐색 과정에서도 문제점을 찾아볼 수 있다. 객체 지향적으로 코드를 작성한 경우 참조를 통해서 자유롭게 객체를 탐색할 수 있다. 하지만 관계형 DB에서는 쿼리를 날리는 순간 탐색의 범위가 결정되므로 엔티티의 신뢰문제가 발생한다. 예를 들어 Member
와 연관관계에 있는 Team
이 있다고 하자. 이때 개발자가 쿼리를 날렸는데 과연 Team
의 정보까지 갖고 왔다고 보장할 수 있을까? 이런 경우 당연히 Team
이 있을거라고 생각하고 조회를 했을 때 null이 발생할 수도 있고 이를 해결하기 위해 쿼리를 날리는 코드까지 확인해봐야하는 불편함이 발생한다. 그렇다고 쿼리를 날리는 시점에서 모든 데이터를 다 가지고 오는 것은 당연히 성능 이슈가 발생한다.
위 상황들을 종합해보았을 때 객체지향적으로 설계를 할 수록 개발자가 해줘야하는 매핑작업만 늘어나는 비효율이 발생하는 것을 알 수 있다. 따라서 객체를 자바 컬렉션을 이용하여 다루듯이 DB에 저장할 수 없을까? 라는 의문점이 필연적으로 발생한다.
이를 해결하기 위해 나타난 기술이 JAVA PERSISTENCE API, JPA이다.