当前位置:网站首页>【云原生】原来2020.0.X版本开始的OpenFeign底层不再使用Ribbon了
【云原生】原来2020.0.X版本开始的OpenFeign底层不再使用Ribbon了
2022-07-25 07:07:00 【秃秃爱健身】
文章目录
一、前言
在前面的Feign系列文章:
- SpringCloud之Feign实现声明式客户端负载均衡详细案例
- SpringCloud之OpenFeign实现服务间请求头数据传递(OpenFeign拦截器RequestInterceptor的使用)
- SpringCloud之OpenFeign的常用配置(超时、数据压缩、日志)
- SpringCloud之OpenFeign的核心组件(Encoder、Decoder、Contract)
- SpringBoot启动流程中开启OpenFeign的入口(ImportBeanDefinitionRegistrar详解)
- 源码剖析OpenFeign如何扫描所有的FeignClient
- 源码剖析OpenFeign如何为FeignClient生成动态代理类
- 图文源码剖析OpenFeign处理请求流程
我们聊了以下内容:
- OpenFeign的概述、为什么会使用Feign代替Ribbon?
- Feign和OpenFeign的区别?
- 详细的OpenFeign实现声明式客户端负载均衡案例
- OpenFeign中拦截器RequestInterceptor的使用
- OpenFeign的一些常用配置(超时、数据压缩、日志输出)
- SpringCloud之OpenFeign的核心组件(Encoder、Decoder、Contract)
- 在SpringBoot启动流程中开启OpenFeign的入口
- OpenFeign如何扫描 / 注册所有的FeignClient
- OpenFeign如何为FeignClient生成动态代理类
- OpenFeign处理请求流程
本文基于OpenFeign高版本(SpringCloud 2020.0.x版本开始之后的版本)讨论:OpenFeign新版本和旧版本之间的差异(高版本OpenFeign底层不使用Ribbon做负载均衡)
PS:本文使用的SpringCloud高版本:
<properties>
<spring-boot.version>2.4.2</spring-boot.version>
<spring-cloud.version>2020.0.1</spring-cloud.version>
<spring-cloud-alibaba.version>2021.1</spring-cloud-alibaba.version>
</properties>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>${spring-boot.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<!--整合spring cloud-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>${spring-cloud.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<!--整合spring cloud alibaba-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-alibaba-dependencies</artifactId>
<version>${spring-cloud-alibaba.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
PS:本文使用的SpringCloud低版本:
<properties>
<spring-boot.version>2.3.7.RELEASE</spring-boot.version>
<spring-cloud.version>Hoxton.SR9</spring-cloud.version>
<spring-cloud-alibaba.version>2.2.6.RELEASE</spring-cloud-alibaba.version>
</properties>
二、源码主流程版本间差异串讲
1、@FeignClientsRegistrar开启对FeignClient的扫描
此处主流程上无区别;
在SpringBoot启动流程中@FeignClientsRegistrar注解开启OpenFeign的入口、OpenFeign扫描所有的FeignClient的流程 高版本和低版本基本一样,低版本的见文章:FeignClientsRegistrar注解开启OpenFeign的入口、OpenFeign扫描所有的FeignClient。
主要流程如下:
1> 开启扫描FeignClient的入口:
- 启动类上添加的
@EnableFeignClients注解会通过@Import注解在SpringBoot启动流程中将ImportBeanDefinitionRegistrar接口的实现类FeignClientsRegistrar注入到启动类的ConfigurationClass的属性中,在注册启动类的BeanDefinition时,会遍历调用其@Import的所有ImportBeanDefinitionRegistrar接口的 registerBeanDefinitions()方法。2> 扫描FeignClient:
- 拿到@EnableFeignClients注解中配置的扫描包路径相关的属性,得到要扫描的包路径;
- 获取到扫描器
ClassPathScanningCandidateComponentProvider,然后给其添加一个注解过滤器(AnnotationTypeFilter),只过滤出包含@FeignClient注解的BeanDefinition;- 扫描器的findCandidateComponents(basePackage)方法从包路径下扫描出所有标注了@FeignClient注解并符合条件装配的接口;然后将其在BeanDefinitionRegistry中注册一下;
2、为FeignClient生成动态代理类
区别主要体现在这里;
在注册FeignClient到Spring容器时,构建的BeanDefinition的beanClas是FeignClientFactoryBean;FeignClientFactoryBean是一个工厂,保存了@FeignClient注解的所有属性值,在Spring容器初始化的过程中,其会根据之前扫描出的FeignClient信息构建FeignClient的动态代理类。
具体的动态代理类生成流程参考博文:OpenFeign如何为FeignClient生成动态代理类;
底层通信Client的区别?
在使用Feign.Builder构建FeignClient的时候,获取到的Client是FeignBlockingLoadBalancerClient(这其中的逻辑后面聊,在OpenFeign低版本是LoadBalancerFeignClient);用于生成FeignClient的Targeter是DefaultTargeter(在OpenFeign低版本是HystrixTargeter,高版本移除了Hystrix,采用Spring Cloud Circuit Breaker 做限流熔断);
具体体现在FeignClientFactoryBean#loadBalance()方法,其是一个进行负载均衡的FeignClient动态代理生成方法;
OpenFeign低版本:
1> FeignBlockingLoadBalancerClient何时注入到Spring容器?
FeignBlockingLoadBalancerClient注入到Spring容器的方式和OpenFeign低版本的LoadBalancerFeignClient是一样的;
进入到FeignBlockingLoadBalancerClient类中,看哪里调用了它唯一一个构造函数;

找到FeignBlockingLoadBalancerClient发现有三个地方调用了它的构造函数,new了一个实例;
- DefaultFeignLoadBalancedConfiguration
- HttpClientFeignLoadBalancedConfiguration
- OkHttpFeignLoadBalancedConfiguration
再结合默认的配置,只有DefaultFeignLoadBalancedConfiguration中的Client符合条件装配;

可以通过引入Apache HttpClient的maven依赖使用HttpClientFeignLoadBalancedConfiguration,
或引入OkHttpClient的maven依赖并在application.yml文件中指定feign.okhttp.enabled属性为true使用OkHttpFeignLoadBalancedConfiguration。
2> DefaultTargeter在哪里注入到Spring容器?
DefaultTargeter注入到Spring容器的方式和OpenFeign低版本的HystrixTargeter是一样的;
在FeignAutoConfiguration类中可以找到Targeter注入到Spring容器的逻辑;

3> 后续生成动态代理类的逻辑和旧版本一样
都体现在ReflectiveFeign#newInstance()方法中:

3、**Client处理负载均衡(核心区别)
上面提到OpenFeign高版本获取到的Client是FeignBlockingLoadBalancerClient,而低版本的是LoadBalancerFeignClient,LoadBalancerFeignClient基于Ribbon实现负载均衡,FeignBlockingLoadBalancerClient就靠OpenFeign自己实现负载均衡;
OpenFeign如何处理一个HTTP请求见博文:图文源码剖析OpenFeign处理请求流程。
接下来浅看一下FeignBlockingLoadBalancerClient是如何做负载均衡的!!
1)FeignBlockingLoadBalancerClient选择一个服务实例

边栏推荐
- Wechat applet request requests to carry cookies to verify whether it has logged in
- Tab bar toggle style
- GIS实战应用案例100篇(十七)-基于DEM制作三维地图
- Can communication test based on STM32: turn the globe
- Boiling short drama Jianghu: nine of the ten production teams are shooting, with a head sharing fund of more than 30million, and users are addicted to paying routines
- Basic usage of thread class
- Octopus network community call 1 starts Octopus Dao construction
- 2022深圳杯
- 常吃发酵馒头是否会伤害身体
- 【SemiDrive源码分析】【驱动BringUp】39 - Touch Panel 触摸屏调试
猜你喜欢

常吃发酵馒头是否会伤害身体

CTF Crypto---RSA KCS1_ Oaep mode

Restrict Su command and sudo mechanism to promote nmap and console command netstat

EFCore高级Saas系统下单DbContext如何支持不同数据库的迁移

Precautions for starting up the server of Dahua Westward Journey

Thread 类的基本用法

代码中的软件工程:正则表达式十步通关

Recycleview realizes horizontal sliding of overlapping items

2022深圳杯

10分钟看懂Jmeter 是如何玩转 redis 数据库的
随机推荐
Standard C language 89
Discuss the important factors that affect the success or failure of automated testing
Common mode inductance has been heard many times, but what principle do you really understand?
分层强化学习综述:Hierarchical reinforcement learning: A comprehensive survey
Argocd user management, RBAC control, script login, APP synchronization
LeetCode118. 杨辉三角
[semidrive source code analysis] [drive bringup] 39 - touch panel touch screen debugging
Leetcode sword finger offer brush question notes
容器内组播
[Yugong series] July 2022 go teaching course 015 assignment operators and relational operators of operators
机器学习两周学习成果
C # --metroframework framework calls the metromodernui library and uses it in the toolbar
Over adapter mode
【SemiDrive源码分析】【驱动BringUp】38 - NorFlash & eMMC分区配置
Octopus network community call 1 starts Octopus Dao construction
百度希壤首场元宇宙拍卖落槌,陈丹青六幅版画作品全部成交!
Precautions for starting up the server of Dahua Westward Journey
Oracle table creation statement template
How to learn C language?
批量导入数据,一直提示 “失败原因:SQL解析失败:解析文件失败::null”怎么回事?