스프링/JPA

[Spring Data JPA] 사용자 정의 레파지토리 생성

imcoding 2022. 9. 26. 20:40

 

 

레파지토리에 구현한 메서드만으로 해결이 어려운 복잡한 쿼리, 동적 쿼리 등은 보통 사용자 정의 레파지토리를 만들어서 해결한다.

 

그리고 핵심 비즈니스 로직이 담긴 쿼리와 그 외 특정 용도로 만든 쿼리를 분리해주는게 베스트 인 것도 이유가 된다.

 

바로 알아보겠다.

 

사용자 정의 레파지토리 생성

public interface MemberRepositoryCustom {
    List<Member> findMemberCustom();
}

사용자 정의 레파지토리를 생성한다.

 

일반적인 인터페이스로 생성하면 되며, 별도의 어노테이션은 기본적으로 없어도 된다.

 

 

임의의 클래스 만들어서 사용자 정의 레파지토리 상속받기

@RequiredArgsConstructor
public class MemberRepositoryImpl implements MemberRepositoryCustom{

    private final EntityManager em;

    @Override
    public List<Member> findMemberCustom() {
        return em.createQuery("select m from Member m")
                .getResultList();
    }
}

사용자 정의 레파지토리를 만들었다면 메서드를 오버라이딩 해 구현할 클래스가 필요하다.

 

클래스를 만들고 원하는 방법으로 DB에 접근하는 메서드를 구현해주면 된다.

 

주의사항 : 사용자 정의 레파지토리의 정상적인 동작을 위해서는 해당 클래스를 명명하는 규칙이 있다.
1. JpaRepository를 상속받는 기존 레파지토리 명 + Impl => MemberRepositoryImpl
2. 사용자 정의 인터페이스 명 + Impl => MemberRepositoryCustomImpl

1, 2번 중 선택해서 명명하면 된다.

 

 

사용자 정의 레파지토리가 JpaRepository 알게 하기

public interface MemberRepository extends JpaRepository<Member, Long>, MemberRepositoryCustom {

}

기존 레파지토리가 JpaRepository와 함께 사용자 정의 레파지토리도 상속받아야 한다.

 

 

동작

위 세 가지 과정으로 사용자 정의 레파지토리 생성과 설정이 끝난다.

 

메서드가 호출되면 사용자 정의 레파지토리에서 사용자 정의 구현 클래스로 이동해 해당 메서드를 작동한다.

(위에서 명명법에 따라 사용자 정의 구현 클래스 이름을 만들어준 이유이다.)

 

각 인터페이스와 클래스가 엮여서 동작하는 방식은 스프링이 제공하는 방식으로, 기존 자바에서 동작하는 것과 차이가 있으니 감안하고 이해하면 된다.