Spring Boot 3.4 中我发现非常重要的下一个特性是通过引入一个全新的测试类 MockMvcTester
来支持 AssertJ 进行 MockMvc
测试。在本文中,我们想深入探讨 Spring Boot 3.4 中的这一新特性,看看它如何帮助我们的 MockMvc
测试并提高测试的可读性。
我为这篇文章编写了一个非常基础的 Spring MVC 控制器,带有一个 /hello
端点:
@RestController
@SpringBootApplication
public class DemoMockmvcApplication {
public static void main(String[] args) {
SpringApplication.run(DemoMockmvcApplication.class, args);
}
@GetMapping("hello")
public String hello(){
return "Hello Spring!";
}
}
通过这种方式,Spring 开发者通常选择
AssertJ
来编写测试中的断言,但对于测试 Spring MVC 控制器中的断言,我们必须使用Hamcrest
匹配器!
@SpringBootTest
@AutoConfigureMockMvc
class DemoMockmvcApplicationTests {
@Autowired
private MockMvc mockMvc;
@Test
void helloEndpoint_shouldReturnHelloMessage_hamcrest() throws Exception {
this.mockMvc.perform(get("/hello"))
.andExpect(status().isOk())
.andExpect(content().string(containsString("Hello Spring!")));
}
}
或者使用 AssertJ
断言在 MockMvc
匹配器中:
@SpringBootTest
@AutoConfigureMockMvc
class DemoMockmvcApplicationTests {
@Autowired
private MockMvc mockMvc;
@Test
void helloEndpoint_shouldReturnHelloMessage_assertj() throws Exception {
this.mockMvc.perform(get("/hello"))
.andExpect(status().isOk())
.andExpect(result -> assertThat(result.getResponse().getContentAsString())
.isEqualTo("Hello Spring!"));
}
}
MockMvcTester 是如何工作的?
从 Spring Boot 3.4 开始,为我们提供了一个自动配置的 MockMvcTester
,它允许我们使用 AssertJ
流畅的 API 定义请求和断言。 MockMvcTester
建立在普通的 MockMvc
之上,并允许我们构建请求并返回一个与 AssertJ
兼容的结果,以便可以将其包装在标准的 assertThat()
方法中。
@SpringBootTest
@AutoConfigureMockMvc
class DemoMockmvcApplicationTests {
@Autowired
private MockMvcTester mockMvcTester;
@Test
void helloEndpoint_shouldReturnHelloMessage_mockMvcTester() {
mockMvcTester.get().uri("/hello").assertThat() //or - assertThat(mockMvcTester.get().uri("/hello"))
.hasStatusOk()
.bodyText().isEqualTo("Hello Spring!");
}
}
使用 MockMvcTester 相较于 MockMvc 的优势
MockMvcTester
是围绕 MockMvc
构建的,但它有几个优势:
- 无需为
AssertJ
断言使用静态导入,因为请求和断言都可以使用流畅的 API 来构建。 - 未解决的异常会得到一致处理,因此您的测试不需要抛出(或捕获)
Exception
(我们需要为MockMvc
处理它) - 默认情况下,无论处理是异步还是同步,断言的结果都是完整的。换句话说,不需要以特殊方式处理异步请求。
- 除了 MockMvcTester 的 AssertJ 断言外,还有几种方法可以在原始的
MockMvc
API 中集成MockMvcTester
与MockMvc
(了解更多方法请点击此处)。
总结
Spring Boot 3.4 中 AssertJ
与 MockMvc
的集成为偏好 AssertJ
而非其他替代方案的 Spring 开发者提供了一种统一编写测试的重要进步。通过 AssertJ
提供的流畅且富有表现力的断言,控制器测试用例的可读性和可维护性将得到提升。
没有回复内容