테스트

쿼리 dsl 테스트 코드작성

이째형 2022. 9. 22. 22:45

@DataJpaTest

리포지토리를 테스트 할 때, @SpringBootTest 어노테이션을 이용할 수도 있지만 ,

@DataJpaTest 어노테이션을 이용하면 더 빠르게 테스트 결과를 확인 할 수 있습니다. 

( @SpringBootTest 어노테이션을 이용할 경우 모든 configuration, context, components를 로드합니다. )

 

@DataJpaTest는 오직 JPA 컴포넌트들만을 테스트하기 위한 어노테이션으로써,  아래와 같이 db연결, jpa 테스트와 연관된 config만 적용되는 것을 확인할 수 있습니다.

 

또한 @Transactional 어노테이션을 보유하고 있어서 테스트 후 자동으로 롤백됩니다.

@AutoConfigureTestDatabase(replace = AutoConfigureTestDatabase.Replace.NONE)

※ 기본적으로 인메모리 데이터베이스를 사용할 수도 있지만, 기존 설정한 db를 사용하려고 한다면 위 코드를 추가해주면 됩니다.

 

- JpaQueryFactory

@DataJpaTest에서 QueryDsl을 이용하기 위해서 jpaQueryFactory를 이용하려면 다음과 같은에러가 발생합니다.

org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type 'com.querydsl.jpa.impl.JPAQueryFactory'

쿼리 dsl 테스트 코드를 작성할 경우, @DataJpaTest를 사용할 수 없을까요?

 

@DataJpaTest를 이용하는 경우에도 EntityManager의 경우 주입을 받을 수 있기 때문에 

@DataJpaTest
class InsuranceHistoryRepositorySupportTest {
    @Autowired
    EntityManager em;
    
    private JPAQueryFactory queryFactory;
    
    @BeforeEach
    void init(){
        queryFactory = new JPAQueryFactory(em);
    }

    @Test
    @DisplayName("어제자 보험가입 요청 조회 성공")
    void findRequestsByInsuranceStepYesterday() {
        //given
        Rider rider = Rider.builder()
                .name("이재형")
                .driverId("dd1234")
                .build();
        em.persist(rider);

        InsuranceHistory history = InsuranceHistory.builder()
                .insuranceStep(2)
                .rider(rider)
                .historyType(HistoryType.REQUEST)
                .createDate(LocalDateTime.now().minusDays(1))
                .build();
        em.persist(history);

        InsuranceHistory history2 = InsuranceHistory.builder()
                .insuranceStep(2)
                .rider(rider)
                .historyType(HistoryType.REQUEST)
                .createDate(LocalDateTime.now().minusDays(2))
                .build();
        em.persist(history2);

        LocalDateTime startDate = LocalDateTime.of(LocalDate.now().minusDays(1), LocalTime.MIN);
        LocalDateTime endDate = LocalDateTime.of(LocalDate.now().minusDays(1),LocalTime.MAX);

        //when
        List<InsuranceHistory> result = queryFactory.selectFrom(insuranceHistory)
                .where(insuranceHistory.insuranceStep.eq(2),
                        insuranceHistory.createDate.between(startDate, endDate))
                .fetch();

        //then
        assertThat(result.size()).isEqualTo(1);
        assertThat(result.get(0).getRider()).isEqualTo(rider);
    }
}

위와 같은 방식으로 @BeforeEach어노테이션을 이용하여 JpaQueryFactory를 이용한 테스트 코드를 작성할 수 있게 됩니다.

 

위 코드로 테스트를 진행하면 다음과 같이 성공 결과를 확인할 수 있습니다.

 

-  @SpringBootTest를 이용하는 경우

@Transactional
@SpringBootTest
class InsuranceHistoryRepositorySpringBootTest {
    @Autowired InsuranceHistoryRepositorySupport insuranceHistoryRepositorySupport;
    @Autowired EntityManager em;

    @Test
    void findRequestsByInsuranceStepYesterday(){
        //given
        Rider rider = Rider.builder()
                .name("이재형")
                .driverId("dd1234")
                .build();
        em.persist(rider);

        InsuranceHistory history = InsuranceHistory.builder()
                .insuranceStep(2)
                .rider(rider)
                .historyType(HistoryType.REQUEST)
                .build();
        em.persist(history);

        InsuranceHistory history2 = InsuranceHistory.builder()
                .insuranceStep(2)
                .rider(rider)
                .historyType(HistoryType.REQUEST)
                .build();
        em.persist(history2);


        //when
        List<InsuranceHistory> result = insuranceHistoryRepositorySupport.findRequestsByInsuranceStepToday(2);

        //then
        assertThat(result.size()).isEqualTo(2);
        assertThat(result.get(0).getRider()).isEqualTo(rider);
    }

}

동일한 테스트를 @SpringBootTest를 이용하여 진행할 경우, 테스트는 성공하지만 @DataJpaTest를 이용했을 때보다 응답 속도가 느리다는 것을 확인할 수 있습니다.

 

 

 

https://www.inflearn.com/questions/23063

 

@DataJpaTest - 인프런 | 질문 & 답변

QueryDsl 강의 잘듣고 있습니다! QueryDsl을 사용하면 @DataJpaTest를 사용하지 못하나요? JPAQueryFactory에 대해서 NoSuchBeanDefinitionException이 발생하는데 따로 주입하는 방법을 모르겠습니다ㅠㅠ - 질문 & 답

www.inflearn.com