Статьи

Плагин Docker Maven для тестирования интеграции

Что такое Докер?

Если вы еще не знаете, что такое Docker, будьте осторожны, вы обнаружите, что используете его так или иначе очень скоро. Остальная часть этого поста предполагает некоторое базовое понимание Docker, но если вы не знакомы с ним сейчас, я уверен, что вы вернетесь позже и прочитаете это.

Docker идеально подходит для интеграционного тестирования, сложных демонстраций распределенных систем или даже запуска производственных систем. Это программный контейнер с открытым исходным кодом. Вы можете представить ее как очень легкую и сверхбыструю виртуальную машину.

Пример

Вдохновленный статьей «Тестирование интеграции с Maven и Docker» и используя Docker Java API, я создал простой плагин Docker Maven, который может управлять контейнерами Docker. Учитывая изображение Docker, плагин создаст из него контейнер и запустит его как часть процесса сборки maven, остановит и удалит контейнер, когда процесс сборки будет завершен. Если изображение недоступно локально, оно извлекает его из общедоступного реестра Docker перед созданием контейнера из него.

Следующий интеграционный тест в Apache Camel игнорируется, поскольку для него требуется работающий экземпляр Redis:

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
package org.apache.camel.component.redis;
 
import org.apache.camel.impl.JndiRegistry;
import org.junit.Ignore;
import org.junit.Test;
import org.springframework.data.redis.connection.jedis.JedisConnectionFactory;
import org.springframework.data.redis.core.RedisTemplate;
 
@Ignore
public class RedisProducerIntegrationTest extends RedisTestSupport {
    private static final JedisConnectionFactory CONNECTION_FACTORY = new JedisConnectionFactory();
 
    static {
        CONNECTION_FACTORY.afterPropertiesSet();
    }
 
    @Override
    protected JndiRegistry createRegistry() throws Exception {
        JndiRegistry registry = super.createRegistry();
        redisTemplate = new RedisTemplate();
        redisTemplate.setConnectionFactory(CONNECTION_FACTORY);
        redisTemplate.afterPropertiesSet();
 
        registry.bind("redisTemplate", redisTemplate);
        return registry;
    }
 
    @Test
    public void shouldSetAString() throws Exception {
        sendHeaders(
                RedisConstants.COMMAND, "SET",
                RedisConstants.KEY, "key1",
                RedisConstants.VALUE, "value");
 
        assertEquals("value", redisTemplate.opsForValue().get("key1"));
    }
 
    @Test
    public void shouldGetAString() throws Exception {
        redisTemplate.opsForValue().set("key2", "value");
        Object result = sendHeaders(RedisConstants.KEY, "key2", RedisConstants.COMMAND, "GET");
 
        assertEquals("value", result);
    }
}

Чтобы это прошло, мы можем использовать docker-maven-plugin с образом Redis и портом 6379, доступным для теста:

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
<plugin>
    <groupId>com.ofbizian</groupId>
    <artifactId>docker-maven-plugin</artifactId>
    <version>1.0.0</version>
    <configuration>
        <images>
            <image>
                <name>dockerfile/redis</name>
                <hostConfig>
                    <![CDATA[
                        {
                            "PortBindings": {
                                "6379/tcp": [
                                    {
                                        "HostIp": "0.0.0.0",
                                        "HostPort": "6379"
                                    }
                                ]
                            }
                        }
                ]]>
                </hostConfig>
            </image>
        </images>
    </configuration>
    <executions>
        <execution>
            <id>start-docker</id>
            <phase>pre-integration-test</phase>
            <goals>
                <goal>start</goal>
            </goals>
        </execution>
        <execution>
            <id>stop-docker</id>
            <phase>post-integration-test</phase>
            <goals>
                <goal>stop</goal>
            </goals>
        </execution>
    </executions>
</plugin>

Плагин запускает контейнер Docker на этапе компиляции, на котором работает экземпляр Redis, и закрывает его на этапе тестирования после интеграции.

Это очень простой пример, но плагин может поддерживать более сложные сценарии с несколькими изображениями, настроенными по-разному и запущенными / остановленными на разных фазах. Наслаждаться.