在 Netflix Feign 中,请求拦截器(Request Interceptor)是一个非常有用的组件。它允许你在每个 Feign 请求发送之前对请求进行自定义操作,比如添加请求头、修改请求参数、记录请求日志等。
请求拦截器在实现诸如认证、授权、统一日志记录等功能时非常方便。如下图:

要创建一个请求拦截器,需要实现 feign.RequestInterceptor 接口。这个接口只有一个方法apply(RequestTemplate template),在这个方法中可以对 RequestTemplate 对象进行操作,该对象包含了即将发送的请求的所有信息,如请求 URL、请求头、请求体等。
以下是一个简单的示例,用于在每个请求中添加一个“X-Forwarded-For”请求头:
// 自定义请求拦截器
static class ForwardedForInterceptor implements RequestInterceptor {
@Override
public void apply(RequestTemplate template) {
template.header("X-Forwarded-For", "origin.host.com");
}
}上面示例中,ForwardedForInterceptor 类实现了 RequestInterceptor 接口。在 apply() 方法中,通过template.header() 方法添加了一个名为“X-Forwarded-For”,值为“origin.host.com”的请求头到请求模板中。
当使用 Feign.builder() 创建 Feign 客户端时,可以通过 requestInterceptor() 方法添加请求拦截器。例如:
// 创建Feign客户端实例的静态方法
static InterceptorFeign create() {
return Feign.builder()
.encoder(new Encoder.Default())
.decoder(new Decoder.Default())
.contract(new Contract.Default())
// 添加请求拦截器
.requestInterceptor(new ForwardedForInterceptor())
.target(InterceptorFeign.class, "http://localhost:8090");
}下面是请求拦截器示例的完整代码:
(1)服务端代码,定义了一个简单的查询服务“/simple/interceptor”,如下:
@GetMapping("/interceptor")
public String interceptor(@RequestHeader("X-Forwarded-For") String xForwardedFor, @RequestParam("msg") String msg) {
return "xForwardedFor=" + xForwardedFor + "<br/>msg=" + msg;
}(2)定义 Feign 客户端代码,如下:
package com.hxstrive.demo_netflix_feign.feign;
import feign.*;
import feign.codec.Decoder;
import feign.codec.Encoder;
/**
* Feign 请求拦截器
* @author HuangXin
*/
public interface InterceptorFeign {
// Feign 请求接口方法
@RequestLine("GET /simple/interceptor?msg={msg}")
String interceptor(@Param("msg") String message);
// 自定义请求拦截器
static class ForwardedForInterceptor implements RequestInterceptor {
@Override
public void apply(RequestTemplate template) {
template.header("X-Forwarded-For", "origin.host.com");
}
}
// 创建Feign客户端实例的静态方法
static InterceptorFeign create() {
return Feign.builder()
.encoder(new Encoder.Default())
.decoder(new Decoder.Default())
.contract(new Contract.Default())
// 添加请求拦截器
.requestInterceptor(new ForwardedForInterceptor())
.target(InterceptorFeign.class, "http://localhost:8090");
}
}(3)调用 Feign 客户端,如下:
@GetMapping("/")
public String index() {
return InterceptorFeign.create().interceptor("hello");
}运行结果如下图:

从上面的输出信息可知,通过请求拦截器成功添加了“X-Forwarded-For”请求头信息。