Feign源码解析:动态代理与HTTP请求全流程
Feign 的源码实现流程可分为 初始化阶段 和 调用阶段 两大核心模块,其底层通过动态代理与模板化 HTTP 请求实现声明式服务调用。以下是关键流程解析:
🔧 一、初始化阶段(启动时)
-
注解扫描与注册
- 通过
@EnableFeignClients
触发FeignClientsRegistrar
扫描所有@FeignClient
标记的接口。 - 为每个接口生成
FeignClientFactoryBean
的 Bean 定义,注册到 Spring 容器。
- 通过
-
动态代理生成
FeignClientFactoryBean.getObject()
方法调用Feign.Builder
构建代理实例:- 使用
ReflectiveFeign
创建 JDK 动态代理,代理逻辑封装在InvocationHandler
中。 - 集成负载均衡客户端(如
LoadBalancerFeignClient
)。
- 使用
-
组件装配
- 从
FeignContext
加载配置的Encoder
、Decoder
、Contract
等组件。
- 从
🔄 二、调用阶段(运行时)
-
代理方法触发
- 调用接口方法时,动态代理的
InvocationHandler
拦截请求,交由SynchronousMethodHandler
处理。
- 调用接口方法时,动态代理的
-
请求模板构造
- 解析方法注解(如
@GetMapping
、@PathVariable
),生成RequestTemplate
(包含 URL、Header、Body 模板)。
- 解析方法注解(如
-
负载均衡与实例选择
- 通过
LoadBalancerFeignClient
结合 Ribbon 或 Spring Cloud LoadBalancer 选择目标服务实例。
- 通过
-
HTTP 请求执行
- 使用底层
Client
(默认HttpURLConnection
,可替换为 OkHttp)发送请求。 - 响应通过
Decoder
反序列化为 Java 对象。
- 使用底层
📦 三、核心类与交互流程
graph LR
A[@FeignClient接口] --> B(FeignClientsRegistrar)
B --> C[FeignClientFactoryBean]
C --> D[Feign.Builder]
D --> E[ReflectiveFeign]
E --> F[JDK动态代理]
F --> G[SynchronousMethodHandler]
G --> H[LoadBalancerFeignClient]
H --> I[HTTP请求]
⚙️ 四、扩展机制
- 自定义组件
- 可通过配置替换
Encoder
、Decoder
或Client
实现。
- 可通过配置替换
- 拦截器
- 实现
RequestInterceptor
可修改请求头或日志记录。
- 实现
- 熔断集成
- 与 Hystrix 或 Resilience4j 结合实现熔断降级。
总结:Feign 通过动态代理将接口调用转化为 HTTP 请求,结合负载均衡与模板化处理实现声明式调用,其设计核心在于 代理生成-模板解析-负载均衡-HTTP 执行 的链路闭环。