[스프링] JPA

gyeol·2023년 7월 7일

스프링

목록 보기
8/50
post-thumbnail

스프링 강의 5일차 😙

김영한님의 '스프링 입문 - 코드로 배우는 스프링 부트, 웹 MVC, DB 접근 기술'을 듣고 적은 글입니다.

✔️ JPA

JDBC -> JDBC TEMPLATE 로 옮겨져 오면서 반복적인 코드를 줄이긴 했으나 SQL은 결국 개발자가 작성해야했다. 하지만 JPA를 사용하면 SQL 쿼리도 자동으로 처리해준다. JPA에 집어 넣으면 SQL을 DB에 날리고 알아서 처리해준다.

JPA : 기존의 반복 코드, 기본적인 SQL도 직접 만들어 실행해준다.
장점 )

  • JPA를 사용하면 SQL과 데이터 중심 설계에 객체 중심 설계로 패러다임을 전환할 수 있다.
  • 개발 생산성을 크게 높일 수 있다.

🔹 buiuld.gradle 파일에 JPA, h2 데이터베이스 관련 라이브러리 추가

JPA 사용을 위해 build.gradle 파일에 JPA, h2 데이터베이스 관련 라이브러리를 추가해준다.

dependencies {
  implementation 'org.springframework.boot:spring-boot-starter-thymeleaf'
  implementation 'org.springframework.boot:spring-boot-starter-web'
  //implementation 'org.springframework.boot:spring-boot-starter-jdbc'
  implementation 'org.springframework.boot:spring-boot-starter-data-jpa'
  runtimeOnly 'com.h2database:h2'
  testImplementation('org.springframework.boot:spring-boot-starter-test') {
  exclude group: 'org.junit.vintage', module: 'junit-vintage-engine'
  }
}

spring-boot-starter-data-jpa 는 내부에 jdbc 관련 라이브러리를 포함한다. 그래서 jdbc를 주석 처리한 것이다.

🔹스프링 부트에 JPA 설정 추가

그리고 resources > application.properties 에 JPA 설정을 추가해준다.

spring.datasource.url=jdbc:h2:tcp://localhost/~/test
spring.datasource.driver-class-name=org.h2.Driver
spring.datasource.username=sa
spring.jpa.show-sql=true
spring.jpa.hibernate.ddl-auto=none

ddl-auto는 JPA가 테이블을 자동으로 생성하는 기능을 제공한다. 지금은 비활성화 시켰지만 활성화 시켜주기 위해서는 create로 바꿔주면 된다.

🔹JPA 엔티티 매핑

그리고 JPA 엔티티 매핑을 위해 이전에 만들어둔 Member.java 파일을 열어 코드를 조금 수정해준다.

package hello.hellospring.domain;

import jakarta.persistence.*;

@Entity
public class Member {

    @Id @GeneratedValue(strategy = GenerationType.IDENTITY)
    // 아이덴티티 : DB에서 ID 자동 생성
    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;
    }
}

🔹 JPA 회원 리포지토리

그리고 JpaMemberRepository.java 파일을 만들어준다.

package hello.hellospring.repository;
import hello.hellospring.domain.Member;
import jakarta.persistence.EntityManager;


import java.util.List;
import java.util.Optional;
public class JpaMemberRepository implements MemberRepository {

    private final EntityManager em;
    
    public JpaMemberRepository(EntityManager em) {
        this.em = em;
    }
    
    public Member save(Member member) {
        em.persist(member);
        return member;
    }
    
    public Optional<Member> findById(Long id) {
        Member member = em.find(Member.class, id);
        return Optional.ofNullable(member);
    }
    
    public List<Member> findAll() {
        return em.createQuery("select m from Member m", Member.class)
                .getResultList();
    }
    
    public Optional<Member> findByName(String name) {
        List<Member> result = em.createQuery("select m from Member m where m.name = :name", Member.class)
                .setParameter("name", name)
                .getResultList();
        return result.stream().findAny();
    }
}

쿼리문을 가만히 보면 우리가 여태 사용한 쿼리문과 조금 다름을 알아챌 수 있다. 보통 쿼리는 테이블 단위로 쿼리를 날리는데, 이 쿼리문은 객체 단위로 대상으로 쿼리를 날리는 것이다. 이를 JPQL 이라고 한다.

JPQL :
JPA는 SQL을 추상화한 JPQL이라는 객체 지향 쿼리 언어를 제공한다. SQL과 문법은 유사하다.
JPQL은 엔티티 객체를 대상으로 쿼리를 질의하고 SQL은 데이터베이스 테이블을 대상으로 쿼리를 질의한다.

🔹 JPA 사용 위해 스프링 설정 변경

package hello.hellospring;
import hello.hellospring.repository.*;
import hello.hellospring.service.MemberService;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import javax.persistence.EntityManager;
import javax.sql.DataSource;

@Configuration
public class SpringConfig {

  private final DataSource dataSource;
  private final EntityManager em;
  
  public SpringConfig(DataSource dataSource, EntityManager em) {
    this.dataSource = dataSource;
    this.em = em;
  }
  
  @Bean
  public MemberService memberService() {
    return new MemberService(memberRepository());
  }
  
  @Bean
  public MemberRepository memberRepository() {
    // return new MemoryMemberRepository();
    // return new JdbcMemberRepository(dataSource);
    // return new JdbcTemplateMemberRepository(dataSource);
    return new JpaMemberRepository(em);
  }
}

그리고 순수 JDBC에서 만든 테스트 케이스를 작성하면 성공적으로 실행되는 것을 알 수 있다.

profile
공부 기록 공간 '◡'

0개의 댓글