在 Spring Boot 中使用单元测试和集成测试

自动化的单元测试,集成测试是项目持续集成的基础。在 Java 平台, JUnit, Mock 以及 Spring Boot Test 为编写自动化测试提供了强大的支持。

本文使用在 Spring Boot 构建Rest服务实验手册(一) 中使用的案例。如果不熟悉的 Spring Boot 的开发,可以先参考该实验手册。

增加依赖库

在 Spring Boot 中,JUnit, Mock 等相关的依赖已经加入到 Spring Boot Test 中,所以只需要在项目中加入如下依赖即可:

1
2
3
4
5
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>

该依赖中默认加入的是 JUnit4

使用 JUnit 编写测试

因为 Spring 框架提倡 POJO 编程,所以一般业务层和展现层的代码都是 POJO, 所以可以直接用 JUnit 进行测试。

下面是测试案例中 TodoApi 的 ok() 方法的例子:

1
2
3
4
5
6
7
8
public class JUnitTodoApiTester {

@Test
public void testOk() {
TodoApi todoApi = new TodoApi();
assertEquals(todoApi.ok(), "ok");
}
}

对于需要调用业务层逻辑的方法,也可以采用 Mock 进行测试,如:

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
26
27
public class MockitoTodoApiTester {

@InjectMocks
private TodoApi todoApi;

@Mock
private TodoBiz todoBiz;

@Before
public void init() {
MockitoAnnotations.initMocks(this);
}

@Test
public void testGetTodoList() {

List<Todo> list = new ArrayList<>();
list.add(new Todo(1, "tom", "desc for tom"));
when(todoBiz.listAll()).thenReturn(list);

ApiResult res = todoApi.getTodoList();

verify(todoBiz).listAll();

assertEquals(true, res.isSucc());
}
}

使用 SpringBootTest 注解

在对 Sprng Boot 应用进行集成测试时,我们希望能启动整个 Spring Boot 的环境来进行测试,这时,可以采用 SpringBootTest 注解。 如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
@RunWith(SpringRunner.class)
@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
public class TodoIntegrationTester {

@LocalServerPort
private int port;

@Autowired
private TestRestTemplate restTemplate;

@Test
public void testOk() throws Exception {

String res = this.restTemplate.getForObject("http://localhost:" + port + "/todo/ok", String.class);
assertEquals(res, "ok");
}
}

在本例中,让应用在一个随机产生的端口启动,然后利用 TestRestTemplate 模拟用户进行访问,从而触发整体的流程来测试一个完整的功能。

如果不需要启动内嵌的服务器,也可以采用 Mock 的方法,如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
@RunWith(SpringRunner.class)
@SpringBootTest
@AutoConfigureMockMvc
public class TodoIntegrationMockTester {

@Autowired
private MockMvc mockMvc;

@Test
public void testOk() throws Exception {

this.mockMvc.perform(get("/todo/ok")).andDo(print()).andExpect(status().isOk()).andExpect(content().string(containsString("ok")));
}
}

同样可以测试一个功能的完整流程。

本文标题:在 Spring Boot 中使用单元测试和集成测试

文章作者:梅老师

发布时间:2019年12月26日 - 14:12

最后更新:2020年09月16日 - 08:09

原始链接:https://www.mls-tech.info/java/springboot-use-testing/

许可协议: 署名-非商业性使用-禁止演绎 4.0 国际 转载请保留原文链接及作者。