在日常开发过程中,经常会用到第三方组件或中间件,如redis,mq,db等。因为这些第三方组件的引入,测试过程会变得复杂起来。可能换了一个环境之后,因为中间件的缺失,测试用例就跑不起来了。而TestContainer可以通过和docker结合,很方便的在代码中启动docker容器,在docker容器中运行这些第三方组件,从而方便进行测试。
基本使用
- 以maven构建的springboot工程为例,引入依赖
<dependency>
<groupId>org.testcontainers</groupId>
<artifactId>testcontainers</artifactId>
<version>1.15.3</version>
<scope>test</scope>
</dependency>
- 配置redisTemplate
@Configuration
public class RedisConfiguration {
@Bean
public RedisTemplate redisTemplate(RedisConnectionFactory connectionFactory) {
RedisTemplate redisTemplate = new RedisTemplate();
redisTemplate.setKeySerializer(new StringRedisSerializer());
redisTemplate.setHashKeySerializer(new StringRedisSerializer());
redisTemplate.setConnectionFactory(connectionFactory);
return redisTemplate;
}
}
- 测试
代码如下:
@SpringBootTest(classes = TestContainer.class)
@RunWith(SpringRunner.class)
public class BasicTests {
@Autowired
private RedisTemplate redisTemplate;
//准备Redis容器,使用withExposedPorts方法暴露端口
@ClassRule
public static GenericContainer redis = new GenericContainer("redis:5.0.5")
.withExposedPorts(6379);
//注意这个注解,要在类加载之前,这样的话,Spring才能拿到这个配置来装配Bean(RedisTempalte),不然这个配置没有意义
@BeforeClass
public static void init() {
//获取容器的IP地址,如果不加设置的话,就是localhost
System.setProperty("spring.redis.host", redis.getContainerIpAddress());
// 获取容器映射出来的端口,如果只有一个,可以使用redis.getFirstMappedPort()
//System.setProperty("spring.redis.port", redis.getFirstMappedPort().toString());
//可以使用另外的方法,明确获取指定容器端口映射出来的宿主机端口,当有多个端口暴露出来的时候,使用这个比较好。
System.setProperty("spring.redis.port", redis.getMappedPort(6379).toString());
}
@Test
public void test() {
redisTemplate.opsForValue().set("k1", "v1");
assert "v1".equals(redisTemplate.opsForValue().get("k1"));
}
@After
public void destory() {
redis.stop();
}
}
在test方法里打上断点,开启debug后(首次运行时需要拉取redis镜像,速度比较慢),在terminal里通过
docker ps
查看当前运行的容器,结果如下:
f61900dca196 redis:5.0.5 "docker-entrypoint.s…" 9 seconds ago Up 8 seconds 0.0.0.0:55007->6379/tcp, :::55007->6379/tcp jovial_payne
972c5233c1c9 testcontainers/ryuk:0.3.1 "/app" 9 seconds ago Up 9 seconds 0.0.0.0:55006->8080/tcp, :::55006->8080/tcp testcontainers-ryuk-8cca32a4-0d78-4c9f-a3
说明redis 容器正在运行。调试结束后,程序通过destory方法停止容器。