Spring Boot - Testcontainers로 MariaDB 테스트하기
Spring Boot로 사이드 프로젝트를 시작하면서 docker를 사용하여 mariadb 환경을 설정했다.
테스트에서도 유사한 환경을 구사하기 위해 Testcontainers 라이브러리를 사용할 수 있었고 그 과정을 기록!! ✍️
실행 환경
- Spring Boot 3.3.4
- Testcontainers 1.20.3
Testcontainers 간략히 알아보기
Testcontainers는 Docker 컨테이너를 활용해 테스트를 수행할 수 있도록 돕는 Java 라이브러리로, 통합 테스트에서 자주 사용된다. 이 라이브러리를 통해 테스트는 독립적이고 일관된 환경에서 실행되며, 실제 운영 환경과 유사한 MariaDB를 사용해 테스트할 수 있다. 특히, 컨테이너 환경에서 테스트가 진행되므로 외부 환경에 영향을 받지 않는다는 장점이 있다.
DataJpaTest 진행해보기
1. Spring Boot 프로젝트에 라이브러리 추가
build.gradle
1
2
3
4
5
dependencies {
testImplementation "org.testcontainers:testcontainers:1.20.3"
testImplementation "org.testcontainers:junit-jupiter:1.20.3"
testImplementation "org.testcontainers:mariadb:1.20.3"
}
2. MariadbTestContainer 객체 생성
profile을 하나만 사용(default profile)하는 경우와 테스트를 위한 test profile을 사용하는 경우에 대해 정리
방법 1. 테스트용 profile이 없는 경우 - test db 계정 정보를 동적으로 설정
MariadbContainer 객체를 생성한 후 @DynamicPropertySource
를 이용해서 동적으로 application.yml의 db 설정을 변경한다.
MariadbTestContainer.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
import org.springframework.test.annotation.DirtiesContext;
import org.springframework.test.context.DynamicPropertyRegistry;
import org.springframework.test.context.DynamicPropertySource;
import org.testcontainers.containers.MariaDBContainer;
import org.testcontainers.junit.jupiter.Container;
import org.testcontainers.junit.jupiter.Testcontainers;
@Testcontainers
@DirtiesContext
class MariadbTestContainer {
@Container
public static final MariaDBContainer mariadb = new MariaDBContainer<>("mariadb:latest")
.withDatabaseName("testdb")
.withUsername("tester")
.withPassword("1234");
@DynamicPropertySource
static void setDatasourceProperties(DynamicPropertyRegistry registry) {
registry.add("spring.datasource.url", mariadb::getJdbcUrl);
registry.add("spring.datasource.username", mariadb::getUsername);
registry.add("spring.datasource.password", mariadb::getPassword);
}
}
@Testcontainers
: Testcontainers 적용@Container
: docker 컨테이너 인스턴스를 생성하고 생명주기를 관리@DynamicPropertySource
: application.yml의 데이터베이스 설정을 테스트 컨테이너의 MariaDB 설정으로 대체하기 위해 사용@DirtiesContext
: 하위 클래스가 동적 프로퍼티를 가진 자체적인 ApplicationContext를 얻을 수 있게 해줌
방법 2. test profile 사용
TestContainer 설정을 test profile(application-test.yml)에 작성한 후 MariadbTestContainer를 실행한다.
MariadbTestContainer.java
1
2
3
4
5
6
7
8
9
10
11
12
13
import org.springframework.test.context.ActiveProfiles;
import org.testcontainers.containers.MariaDBContainer;
import org.testcontainers.junit.jupiter.Container;
import org.testcontainers.junit.jupiter.Testcontainers;
@ActiveProfiles("test")
@Testcontainers
class MariadbTestContainer {
@Container
public static final MariaDBContainer mariadb = new MariaDBContainer<>("mariadb:latest");
}
@Testcontainers
: Testcontainers 적용@Container
: docker 컨테이너 인스턴스를 생성하고 생명주기를 관리
application-test.yml
1
2
3
4
5
6
spring:
datasource:
url: jdbc:tc:mariadb://testdb
username: tester
password: 1234
3. DataJpaTest 작성
SiteRepositoryTest.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.autoconfigure.jdbc.AutoConfigureTestDatabase;
import org.springframework.boot.test.autoconfigure.orm.jpa.DataJpaTest;
@DataJpaTest
@AutoConfigureTestDatabase(replace = AutoConfigureTestDatabase.Replace.NONE)
class SiteRepositoryTest extends MariadbTestContainer {
@Autowired private SiteRepository siteRepository;
@Test
void test() {
List<SiteEntity> siteEntityAll = siteRepository.findAll();
assertThat(siteEntityAll.size()).isZero();
}
}
@AutoConfigureTestDatabase(replace = AutoConfigureTestDatabase.Replace.NONE)
- DataJpaTest에서 H2 등 임베디드 DB를 사용하지 않고 application.yml 설정 적용
참고한 사이트
- https://testcontainers.com/guides/getting-started-with-testcontainers-for-java/
- https://www.atomicjar.com/2023/11/whats-new-with-testcontainers-in-spring-boot-3-2-0/
- https://docs.spring.io/spring-framework/docs/current/javadoc-api/org/springframework/test/context/DynamicPropertySource.html
- https://velog.io/@langoustine/%ED%85%8C%EC%8A%A4%ED%8A%B8-%EC%BB%A8%ED%85%8C%EC%9D%B4%EB%84%88%EB%A5%BC-%ED%99%9C%EC%9A%A9%ED%95%B4-%ED%86%B5%ED%95%A9%ED%85%8C%EC%8A%A4%ED%8A%B8-%EC%88%98%ED%96%89%ED%95%98%EA%B8%B0
이 기사는 저작권자의 CC BY 4.0 라이센스를 따릅니다.