1. 概述

在本教程中,我们将深入探讨 Spring WebFlux 中的 WebClient 过滤器机制。作为 Spring 提供的函数式响应式 Web 框架,WebFlux 中的 WebClient 是构建非阻塞 HTTP 客户端的核心工具之一。而过滤器(Filter)机制则为统一处理请求提供了强大的能力。

2. 请求过滤器简介

过滤器可以拦截、检查并修改客户端的请求或响应。它非常适合在所有请求中统一添加某些逻辑,例如日志记录、身份验证、监控等,从而避免重复代码,提升可维护性。

在 Spring Reactive 中,过滤器是 ExchangeFilterFunction 类型的实例。这个函数式接口有两个参数:一个是当前的 ClientRequest,另一个是下一个过滤器函数 ExchangeFilterFunction

一个简单的过滤器实现如下:

ExchangeFilterFunction filterFunction = (clientRequest, nextFilter) -> {
    LOG.info("WebClient filter executed");
    return nextFilter.exchange(clientRequest);
};

✅ 注意:过滤器链是有序的,每个过滤器都应调用 nextFilter.exchange(clientRequest) 来继续执行后续逻辑。

3. 将过滤器绑定到 WebClient

定义好过滤器后,我们需要将其绑定到 WebClient 实例上。这个绑定只能在创建 WebClient 时完成

通常我们有两种方式创建 WebClient:

  • 简单创建(无法添加过滤器):
WebClient webClient = WebClient.create();
  • 构造器方式(推荐,支持添加过滤器):
WebClient webClient = WebClient.builder()
  .filter(filterFunction)
  .build();

✅ 所以如果你想使用过滤器功能,**必须使用 WebClient.builder()**。

4. 自定义过滤器实战

4.1 统计 GET 请求次数

我们可以定义一个过滤器来统计所有发出的 GET 请求:

ExchangeFilterFunction countingFunction = (clientRequest, nextFilter) -> {
    HttpMethod httpMethod = clientRequest.method();
    if (httpMethod == HttpMethod.GET) {
        getCounter.incrementAndGet(); // 假设 getCounter 是一个 AtomicInteger
    }
    return nextFilter.exchange(clientRequest);
};

4.2 修改请求 URL 添加版本号

下面这个过滤器会修改请求的 URL,在路径末尾加上版本号:

ExchangeFilterFunction urlModifyingFilter = (clientRequest, nextFilter) -> {
    String oldUrl = clientRequest.url().toString();
    URI newUrl = URI.create(oldUrl + "/" + version);
    ClientRequest filteredRequest = ClientRequest.from(clientRequest)
      .url(newUrl)
      .build();
    return nextFilter.exchange(filteredRequest);
};

4.3 请求日志记录

记录每次请求的方法和 URL,方便调试和监控:

ExchangeFilterFunction loggingFilter = (clientRequest, nextFilter) -> {
    printStream.print("Sending request " + clientRequest.method() + " " + clientRequest.url());
    return nextFilter.exchange(clientRequest);
};

5. 常用标准过滤器示例

除了自定义过滤器,Spring WebFlux 也提供了一些开箱即用的过滤器。例如:

5.1 基础认证(Basic Authentication)

这是最常见的认证方式之一,可以直接使用 Spring 提供的过滤器:

WebClient webClient = WebClient.builder()
  .filter(ExchangeFilterFunctions.basicAuthentication(username, password))
  .build();

⚠️ 注意:这里的 usernamepassword 需要替换成实际的凭证。

6. 总结

本文介绍了 Spring WebFlux 中 WebClient 的过滤器机制,包括:

  • 过滤器的作用和基本结构
  • 如何将过滤器绑定到 WebClient
  • 自定义统计、URL 修改、日志记录等常见用例
  • 使用 Spring 提供的标准过滤器(如 Basic Auth)

如果你希望在项目中统一处理请求逻辑,过滤器是一个非常实用且推荐的方式

完整示例代码请参考 GitHub:Spring WebClient Filters 示例(原文链接,可替换为你自己的仓库地址)


原始标题:Spring WebClient Filters