You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何为ClientResponseErrorService.genericClientFilter编写JUnit测试获取覆盖率

问题根因及修复方案

1. 过滤器代码存在逻辑错误

你当前的过滤器实现中,错误状态分支的响应处理流没有被正确返回,导致clientResponse.bodyToMono创建的冷流没有被订阅执行,且原错误响应直接透传给了WebClient默认的错误处理器,抛出了内置的WebClientResponseException,这是你代码执行到对应行未生效的核心原因。
原错误代码片段:

if (clientResponse.statusCode().isError()) {
  // 此处创建的Mono没有被返回,不会被订阅执行
  clientResponse.bodyToMono(String.class).flatMap(clientResponseBody -> {
    try {
      log.info("Into error Handler");
      return Mono.error(getException(clientResponse, clientResponseBody));
    } catch (Exception ex) {
      return Mono.error(getException(clientResponse, clientResponseBody));
    }
  });
  // 直接返回了原响应,走WebClient默认错误处理逻辑
  return Mono.just(clientResponse);
}

修正后的过滤器代码:

public static ExchangeFilterFunction genericClientFilterFunction() {
    return ExchangeFilterFunction.ofResponseProcessor(clientResponse -> {
      if (clientResponse.statusCode().isError()) {
        // 直接返回处理后的错误流,让订阅者触发执行
        return clientResponse.bodyToMono(String.class).flatMap(clientResponseBody -> {
          try {
            log.info("Into error Handler");
            return Mono.error(getException(clientResponse, clientResponseBody));
          } catch (Exception ex) {
            return Mono.error(getException(clientResponse, clientResponseBody));
          }
        });
      } else {
        return Mono.just(clientResponse);
      }
    });
}

2. 测试代码逻辑不符合预期

你当前测试的是错误响应场景,请求返回400、401都是错误码,整个流最终会抛出异常,不会正常返回响应体,所以expectNextCount(1)的断言本身就不成立。同时你加了retry(1)会触发两次请求,如果MockWebServer队列中响应数量不匹配会返回404错误。
修正后的单场景测试代码示例:

@Test
public void exchangeFilterFunctionTest_400Error() throws Exception {
    // 入队单个400错误响应
    server.enqueue(new MockResponse()
        .addHeader("Content-Type", "application/json; charset=utf-8")
        .setBody("{}")
        .setResponseCode(400));
    
    WebClient webClient = WebClient.builder()
        .baseUrl("http://localhost:" + server.getPort())
        .filter(ClientResponseErrorService.genericClientFilterFunction())
        .build();
    
    Mono<String> responseMono = webClient.get()
        .uri("/api")
        .retrieve()
        .bodyToMono(String.class);
    
    // 断言抛出你自定义的异常类型,替换成你getException方法返回的实际异常类
    StepVerifier.create(responseMono)
        .expectError(YourCustomException.class)
        .verify();
}

如果需要测试重试逻辑,也可以对应调整断言,验证两次请求后抛出预期异常即可。

内容的提问来源于stack exchange,提问作者Harsh Kanakhara

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.17 14:36:00