ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • SpringDataJPA (1) - 공용 인터페이스, @Query
    Web/JPA 2024. 1. 30. 15:18

     

    1. 공용 인터페이스 설정 

     

    - JavaConfig 설정 (부트 사용시 생략 가능)

    @Configuration
    @EnableJpaRepositories(basePackages = "jpabook.jpashop.repository")
    public class AppConfig {}

     

    - 스프링 부트 사용시 @SpringBootApplication 위치를 지정 

    - 만약 위치가 달라지면 @EnableJpaRepositories필요 

    - org.springframework.data.repository.Repository를 구현 클래스는 스캔 대상이 된다.

    - 프록시로 동작한다.

    - @Repository 어노테이션은 JPA 예외를 스프링 예외로 변환하는 과정을 처리한다. 

    - 컴포넌트 스캔을 스프링 데이터 JPA가 자동으로 처리 (인터페이스에 생략가능)

     

    public interface MemberRepository extends JpaRepository<Member, Long> {
    }
    
    //JpaRepositroy인터페이스를 상속하고, 타입으로 엔티티 클래스와 기본 키 타입 넣음

     

    - 대부분의 간단한 메서드는 이미 내부적으로 구현되어 있다.

     

    2. 공용 인터페이스 분석 

     

    - JpaRepositroy 인터페이스 : 공통 CRUD 제공

    - 제네릭은 <엔티티 타입, 식별자 타입> 설정 

     

    출처: springDataJpa(김영한) - 인프런

     

    - T findOne(ID) -> Optional<T> findById(ID)로 변경

    - boolean exists(ID) -> boolean existsById(ID)로 변경

     

    제네릭 타입 : T (엔티티), ID(엔티티의 식별자 타입), S(엔티티와 그 자식타입)

     

    - 주요메서드:

    save : 새로운 엔티티는 저장하고 이미 있는 엔티티 병합

    delete : 엔티티 하나 삭제 (내부에서 em.remove 호출)

    findbyID : 엔티티 하나 조회 (em.find)

    getOne : 엔티티를 프록시로 조회 (em.getReference() 호출)

    findAll : 모든 엔티티 조회, 정렬이나 페이징 조건을 파라미터로 제공 가능 

     

     

     

    3. 쿼리 메소드 기능 

     

     

    3.1 메소드 이름으로 쿼리 생성

     

    - 메소드 이름을 분석해서 JPQL 쿼리 생성함

     

    List<Member> findByUsernameAndAgeGreaterThan(String username, int age)

     

    > 조회 : find...By, read...By, query...By, get...By

                 ...에는 메소드 식별을 위한 내용이 들어가도 된다. (findHello)

    > COUNT: count...By 반환타입 long

    > EXISTS: exists...BY 반환타입 boolean

    > 삭제 : delete...By, remove...By 반환타입 long

    > DISTINCT: findDistinct, findMemberDistinctBy

    > LIMIT : findFrist3, findFirst,findTop,findTop3

     

    -> 더 많은 규칙은 jpa공식문서를 찾아보자

     

    * 엔티티의 필드명이 변경되면 인터페이스에 정의한 메서드 이름도 꼭 함께 변경해야한다. 그렇지 않으면, 애플리케이션 시작 시잠에 오류발생 (이거 장점이다!)

     

    3.2 JPA NamedQuery 기능

     

    - 잘 사용하지 않는다. 필요시 찾아보자

     

     

    3.3 @Query 

     

    - 리포지토리 메소드에 쿼리를 정의하는 방법이다.

    public interface MemberRepository extends JpaRepository<Member, Long> {
    
    	@Query("select m from Member m where m.username = :username and m.age = :age")
        List<Member> findUser(@Param("username") String username, @Param("age") int age); 
    }

     

    - @org.springframwork.data.jpa.repository.Query 어노테이션을 사용

    - 실행할 메서드에 정적 쿼리를 직접 작성하므로 이름 없는 Named 쿼리라 할 수 있음

    - JPA Named 쿼리처럼 애플리케이션 실행 시점에 문법 오류 발견할 수 있음 > 매우 큰 장점

     

    -> @Query 값 DTO 조회하기

     

    단순히 값 하나를 조회

    @Query("select m.username from Member m")
    List<String> findUsernameList();
    //JPA 임베디드 타입도 이 방식으로 조회 가능 
    
    @Query("select new study.datajpa.dto.MemberDto(m.id,m.usrname,t.name) from Member m join m.team t")
    List<MemberDto> findMemberDto();

     

    -> 파라미터 바인딩 

     

    - 이름 기반만 사용하자! 

    @Query("select m from Member m where m.username = :name")
    Member findMembers(@Param("name") String username)

     

    - >컬렉션 파라미터 바인딩

    @Query("select m from Member m where m.username in :names")
    List<Member> findByNames(@Param("names") List<String> names);

     

    - > 반환 타입 (jpa는 유연한 반환 타입 지원)

     

    List<Member> findByUsername(String name)
    Member findByUsername(String name)
    Optional<Member> findByUsername(String name)

     

    -> 조회 결과가 많거나 없으면?

      

      컬렉션 : 빈 컬렉션 반환

      단건조회: null반환 (2건이상 반환시 예외발생)

     

     

Designed by Tistory.