如何在@WebFluxTest测试中使用WebClient替代WebTestClient测试Spring Boot控制器
@WebFluxTest中使用WebClient的规范实现方案
不需要通过反射从WebTestClient提取ExchangeFunction,Spring官方提供了两种开箱即用的合规实现方式:
方案1:注入测试上下文预配置的WebClient.Builder
@WebFluxTest切片测试启动时,会自动在上下文初始化适配控制器测试的WebClient.Builder实例,该实例已内置和WebTestClient一致的模拟调用ExchangeFunction,不会发起真实网络请求,直接注入使用即可。
示例代码:
import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.Test; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.boot.test.autoconfigure.web.reactive.WebFluxTest; import org.springframework.web.reactive.function.client.WebClient; import reactor.core.publisher.Mono; import reactor.test.StepVerifier; @WebFluxTest(YourTargetController.class) public class YourControllerTest { @Autowired private WebClient.Builder webClientBuilder; private WebClient webClient; @BeforeEach void initWebClient() { webClient = webClientBuilder.build(); } @Test void testApiEndpoint() { Mono<String> result = webClient.get() .uri("/test/endpoint") .retrieve() .bodyToMono(String.class); StepVerifier.create(result) .expectNext("expected response") .verifyComplete(); } }
方案2:手动绑定控制器构造WebClient(无Spring上下文轻量测试)
如果不需要启动Spring测试上下文,只做纯控制器单元测试,可以通过WebTestClient的公开API直接获取ExchangeFunction构造WebClient,全程无反射操作:
示例代码:
import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.Test; import org.springframework.test.web.reactive.server.WebTestClient; import org.springframework.web.reactive.function.client.ExchangeFunction; import org.springframework.web.reactive.function.client.WebClient; import reactor.core.publisher.Mono; import reactor.test.StepVerifier; public class YourControllerUnitTest { private WebClient webClient; @BeforeEach void initWebClient() { // 手动绑定目标控制器实例,无反射调用 ExchangeFunction exchangeFunction = WebTestClient.bindToController(new YourTargetController()) .build() .mutate() .build() .getExchangeFunction(); webClient = WebClient.builder() .exchangeFunction(exchangeFunction) .build(); } @Test void testApiEndpoint() { Mono<String> result = webClient.get() .uri("/test/endpoint") .retrieve() .bodyToMono(String.class); StepVerifier.create(result) .expectNext("expected response") .verifyComplete(); } }
两种方案的优势
- 完全符合Spring官方API规范,没有反射操作,兼容性不随Spring版本升级失效
- 底层均为模拟调用,不会启动HTTP服务,测试执行效率和WebTestClient原生方案一致
- 完全保留WebClient原生API使用习惯,无需适配WebTestClient的特殊断言逻辑
内容的提问来源于stack exchange,提问作者MeIr
相关产品推荐
相关产品推荐

