Перейти к основному содержимому

Настройка отдельного источника данных Spring для тестов

· 4 мин. чтения

1. Обзор

При тестировании приложения Spring, основанного на уровне сохраняемости, таком как JPA, мы можем захотеть настроить источник тестовых данных для использования меньшей и более быстрой базы данных — той, которая отличается от той, которую мы используем для запуска приложения, — чтобы чтобы сделать наши тесты намного проще.

Настройка источника данных в Spring требует определения bean-компонента типа DataSource либо вручную, либо, при использовании Spring Boot, через стандартные свойства приложения.

В этом кратком руководстве мы рассмотрим несколько способов настройки отдельного источника данных для тестирования в Spring .

2. Зависимости Maven

Мы собираемся создать приложение Spring Boot с использованием Spring JPA и тестирования, поэтому нам понадобятся следующие зависимости:

<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
<dependency>
<groupId>com.h2database</groupId>
<artifactId>h2</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
</dependency>

Последние версии spring-boot-starter-data-jpa , h2 и spring-boot-starter-test можно загрузить с Maven Central.

Давайте рассмотрим несколько различных способов настройки источника данных для тестирования.

3. Использование стандартного файла свойств в Spring Boot

Стандартный файл свойств, который Spring Boot автоматически выбирает при запуске приложения, называется application.properties и находится в папке src/main/resources .

Если мы хотим использовать разные свойства для тестов, то мы можем переопределить файл свойств в основной папке, поместив другой файл с таким же именем в src/test/resources .

Файл application.properties в папке src/test/resources должен содержать стандартные пары ключ-значение, необходимые для настройки источника данных. Эти свойства имеют префикс spring.datasource .

Например, давайте настроим базу данных H2 в памяти в качестве источника данных для тестов:

spring.datasource.driver-class-name=org.h2.Driver
spring.datasource.url=jdbc:h2:mem:db;DB_CLOSE_DELAY=-1
spring.datasource.username=sa
spring.datasource.password=sa

Spring Boot будет использовать эти свойства для автоматической настройки bean-компонента DataSource .

Давайте определим очень простой GenericEntity и репозиторий, используя Spring JPA:

@Entity
public class GenericEntity {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
private String value;

//standard constructors, getters, setters
}
public interface GenericEntityRepository
extends JpaRepository<GenericEntity, Long> { }

Далее давайте напишем тест JUnit для репозитория. Чтобы тест в приложении Spring Boot мог использовать определенные нами стандартные свойства источника данных, он должен быть аннотирован с помощью @SpringBootTest :

@RunWith(SpringRunner.class)
@SpringBootTest(classes = Application.class)
public class SpringBootJPAIntegrationTest {

@Autowired
private GenericEntityRepository genericEntityRepository;

@Test
public void givenGenericEntityRepository_whenSaveAndRetreiveEntity_thenOK() {
GenericEntity genericEntity = genericEntityRepository
.save(new GenericEntity("test"));
GenericEntity foundEntity = genericEntityRepository
.findOne(genericEntity.getId());

assertNotNull(foundEntity);
assertEquals(genericEntity.getValue(), foundEntity.getValue());
}
}

4. Использование пользовательского файла свойств

Если мы не хотим использовать стандартный файл application.properties и ключи или если мы не используем Spring Boot, мы можем определить собственный файл .properties с пользовательскими ключами, а затем прочитать этот файл в классе @Configuration , чтобы создать bean- компонент DataSource на основе содержащихся в нем значений.

Этот файл будет помещен в папку src/main/resources для нормального режима работы приложения и в папку src/test/resources для того, чтобы его могли использовать тесты.

Давайте создадим файл с именем persistence-generic-entity.properties , который использует базу данных H2 в памяти для тестов, и поместим его в папку src/test/resources :

jdbc.driverClassName=org.h2.Driver
jdbc.url=jdbc:h2:mem:db;DB_CLOSE_DELAY=-1
jdbc.username=sa
jdbc.password=sa

Затем мы можем определить bean- компонент DataSource на основе этих свойств в классе @Configuration , который загружает наш persistence-generic-entity.properties в качестве источника свойств:

@Configuration
@EnableJpaRepositories(basePackages = "org.foreach.repository")
@PropertySource("persistence-generic-entity.properties")
@EnableTransactionManagement
public class H2JpaConfig {
// ...
}

Более подробный пример этой конфигурации можно найти в нашей предыдущей статье « Автономное тестирование с базой данных в памяти », раздел «Конфигурация JPA».

Затем мы можем создать тест JUnit , аналогичный предыдущему, за исключением того, что он загрузит наш класс конфигурации:

@RunWith(SpringRunner.class)
@SpringBootTest(classes = {Application.class, H2JpaConfig.class})
public class SpringBootH2IntegrationTest {
// ...
}

5. Использование профилей Spring

Другой способ настроить отдельный источник данных для тестирования — использовать профили Spring для определения bean-компонента DataSource , который доступен только в тестовом профиле.

Для этого мы можем использовать файл .properties , как и раньше, или мы можем записать значения в самом классе.

Давайте определим bean-компонент DataSource для тестового профиля в классе @Configuration , который будет загружен нашим тестом:

@Configuration
@EnableJpaRepositories(basePackages = {
"org.foreach.repository",
"org.foreach.boot.repository"
})
@EnableTransactionManagement
public class H2TestProfileJPAConfig {

@Bean
@Profile("test")
public DataSource dataSource() {
DriverManagerDataSource dataSource = new DriverManagerDataSource();
dataSource.setDriverClassName("org.h2.Driver");
dataSource.setUrl("jdbc:h2:mem:db;DB_CLOSE_DELAY=-1");
dataSource.setUsername("sa");
dataSource.setPassword("sa");

return dataSource;
}

// configure entityManagerFactory
// configure transactionManager
// configure additional Hibernate properties
}

Затем в тестовом классе JUnit нам нужно указать, что мы хотим использовать тестовый профиль, добавив аннотацию @ActiveProfiles :

@RunWith(SpringRunner.class)
@SpringBootTest(classes = {
Application.class,
H2TestProfileJPAConfig.class})
@ActiveProfiles("test")
public class SpringBootProfileIntegrationTest {
// ...
}

6. Заключение

В этом кратком руководстве мы рассмотрели несколько способов настройки отдельного источника данных для тестирования в Spring.

Как всегда, полный исходный код примеров можно найти на GitHub .