成人免费xxxxx在线视频软件_久久精品久久久_亚洲国产精品久久久_天天色天天色_亚洲人成一区_欧美一级欧美三级在线观看

OpenFeign的9個坑,每個都能讓你的系統奔潰

開發 架構
OpenFeign是SpringCloud中的重要組件,它是一種聲明式的HTTP客戶端。使用OpenFeign調用遠程服務就像調用本地方法一樣,但是如果使用不當,很容易踩到坑。

[[412891]]

本文轉載自微信公眾號「程序員jinjunzhu」,作者jinjunzhu。轉載本文請聯系程序員jinjunzhu公眾號。

OpenFeign是SpringCloud中的重要組件,它是一種聲明式的HTTP客戶端。使用OpenFeign調用遠程服務就像調用本地方法一樣,但是如果使用不當,很容易踩到坑。

坑一:用對Http Client

1.1 feign中http client

如果不做特殊配置,OpenFeign默認使用jdk自帶的HttpURLConnection,我們知道HttpURLConnection沒有連接池、性能和效率比較低,如果采用默認,很可能會遇到性能問題導致系統故障。

可以采用Apache HttpClient,properties文件中增加下面配置:

  1. feign.httpclient.enabled=true 

pom文件中增加依賴:

  1. <dependency> 
  2.     <groupId>io.github.openfeign</groupId> 
  3.     <artifactId>feign-httpclient</artifactId> 
  4.     <version>9.3.1</version> 
  5. </dependency> 

也可以采用OkHttpClient,properties文件中增加下面配置:

  1. feign.okhttp.enabled=true 

pom文件中增加依賴:

  1. <dependency> 
  2.     <groupId>io.github.openfeign</groupId> 
  3.     <artifactId>feign-okhttp</artifactId> 
  4.     <version>10.2.0</version> 
  5. </dependency> 

1.2 ribbon中的Http Client

通過OpenFeign作為注冊中心的客戶端時,默認使用Ribbon做負載均衡,Ribbon默認也是用jdk自帶的HttpURLConnection,需要給Ribbon也設置一個Http client,比如使用okhttp,在properties文件中增加下面配置:

  1. ribbon.okhttp.enabled=true 

坑二:全局超時時間

OpenFeign可以設置超時時間,簡單粗暴,設置一個全局的超時時間,如下:

  1. feign.client.config.default.connectTimeout=2000 
  2. feign.client.config.default.readTimeout=60000 

如果不配置超時時間,默認是連接超時10s,讀超時60s,在源碼feign.Request的內部類Options中定義。

這個接口設置了最大的readTimeout是60s,這個時間必須大于調用的所有外部接口的readTimeout,否則處理時間大于readTimeout的接口就會調用失敗。

如下圖,在一個系統中使用OpenFeign調用外部三個服務,每個服務提供兩個接口,其中serviceC的一個接口需要60才能返回,那上面的readTimeout必須設置成60s。

但是如果serviceA出故障了,表現是接口1超過60s才能返回,這樣OpenFeign只能等到讀超時,如果調用這個接口的并發量很高,會大量占用連接資源直到資源耗盡系統奔潰。要防止這樣的故障發生,就必須保證接口1能fail-fast。最好的做法就是給serviceC單獨設置超時時間。

坑三:單服務設置超時時間

從上一節的講解我們看到,需要對serviceC單獨設置一個超時時間,代碼如下:

  1. feign.client.config.serviceC.connectTimeout=2000 
  2. feign.client.config.serviceC.readTimeout=60000 

這個時間會覆蓋第一節中默認的超時時間。但是問題又來了,serviceC中又掉了serviceD,因為serviceD的故障導致接口6發生了讀超時的情況,為了不讓系統奔潰,不得不對serviceC的接口5單獨設置超時時間。如下圖:

坑四:熔斷超時時間

怎樣給單個接口設置超時時間,查看網上資料,必須開啟熔斷,配置如下:

  1. feign.hystrix.enabled=true 

開啟熔斷后,就可以給單個接口配置超時了。如果調用serviceC的接口5的聲明如下:

  1. @FeignClient(value = "serviceC"configuration = FeignMultipartSupportConfig.class) 
  2. public interface ServiceCClient { 
  3.     @GetMapping("/interface5"
  4.     String interface5(String param); 

根據上面interface5接口的聲明,在properties文件中增加如下配置:

  1. hystrix.command.ServiceCClient#interface5(param).execution.isolation.thread.timeoutInMilliseconds=60000 

網上資料說的并不準確,這個超時時間并沒有起作用。為什么不生效呢?

4.1 使用feign超時

最終使用的超時時間來自于Options類。如果我們配置了feign的超時時間,會選擇使用feign超時時間,下面代碼在FeignClientFactoryBean類的configureUsingProperties方法:

  1. if (config.getConnectTimeout() != null && config.getReadTimeout() != null) { 
  2.  builder.options(new Request.Options(config.getConnectTimeout(), config.getReadTimeout())); 

4.2 使用ribbon超時

如果沒有配置feign,但是配置了ribbon的超時時間,會使用ribbon的超時時間。我們看下這段源代碼,FeignLoadBalancer里面的execute方法,

  1. public RibbonResponse execute(RibbonRequest request, IClientConfig configOverride) 
  2.   throws IOException { 
  3.  Request.Options options; 
  4.  if (configOverride != null) { 
  5.   RibbonProperties override = RibbonProperties.from(configOverride); 
  6.   options = new Request.Options( 
  7.     override.connectTimeout(this.connectTimeout), 
  8.     override.readTimeout(this.readTimeout)); 
  9.  } 
  10.  else { 
  11.   options = new Request.Options(this.connectTimeout, this.readTimeout); 
  12.  } 
  13.  //這個request里面的client就是OkHttpClient 
  14.  Response response = request.client().execute(request.toRequest(), options); 
  15.  return new RibbonResponse(request.getUri(), response); 

4.3 使用自定義Options

對于單個接口怎么配置超時時間,我這里給出一個方案,如果你有其他方案,歡迎探討。我的方案是使用RestTemplate來調這個接口,單獨配置超時時間,配置代碼如下,這里使用OkHttpClient:

  1. public class RestTemplateConfiguration { 
  2.   
  3.     @Bean 
  4.     public OkHttp3ClientHttpRequestFactory okHttp3RequestFactory(){ 
  5.         OkHttp3ClientHttpRequestFactory requestFactory = new OkHttp3ClientHttpRequestFactory(); 
  6.         requestFactory.setConnectTimeout(2000); 
  7.         requestFactory.setReadTimeout(60000); 
  8.         return requestFactory; 
  9.     } 
  10.   
  11.     @Bean 
  12.     @LoadBalanced 
  13.     public RestTemplate restTemplate(OkHttp3ClientHttpRequestFactory okHttp3RequestFactory){ 
  14.         return new RestTemplate(okHttp3RequestFactory); 
  15.     } 

為了使用ribbon負載均衡,上面加了@LoadBalanced

如果使用RestTemplate,就會使用OkHttp3ClientHttpRequestFactory中配置的時間。

坑五:ribbon超時時間

作為負載均衡,ribbon超時時間也是可以配置的,可以在properties增加下面配置:

  1. ribbon.ConnectTimeout=2000 
  2. ribbon.ReadTimeout=11000 

有文章講ribbon配置的超時時間必須要滿足接口響應時間,其實不然,配置feign的超時時間就足夠了,因為它可以覆蓋掉ribbon的超時時間。

坑六:重試默認不開啟

OpenFeign默認是不支持重試的,可以在源代碼FeignClientsConfiguration中feignRetryer中看出。

  1. @Bean 
  2. @ConditionalOnMissingBean 
  3. public Retryer feignRetryer() { 
  4.  return Retryer.NEVER_RETRY; 

要開啟重試,我們可以自定義Retryer,比如下面這行代碼:

  1. Retryer retryer = new Retryer.Default(100, 1000, 2); 

表示每間隔100ms,最大間隔1000ms重試一次,最大重試次數是1,因為第三個參數包含了第一次請求。

坑七:Ribbon重試

7.1 拉取服務列表

Ribbon默認從服務端拉取列表的時間間隔是30s,這個對優雅發布很不友好,一般我們會把這個時間改短,如下改成3s:

  1. serviceC.ribbon.ServerListRefreshInterval=3 

7.2 重試

Ribbon重試有不少需要注意的地方,這里分享4個。

1.同一實例最大重試次數,不包括首次調用,配置如下:

  1. serviceC.ribbon.MaxAutoRetries=1 

這個次數不包括首次調用,配置了1,重試策略會先嘗試在失敗的實例上重試一次,如果失敗,請求下一個實例。

2.同一個服務其他實例的最大重試次數,這里不包括第一次調用的實例。默認值為1:

  1. serviceC.ribbon.MaxAutoRetriesNextServer=1 

3.是否對所有操作都重試,如果改為true,則對所有操作請求都進行重試,包括post,建議采用默認配置false。

  1. serviceC.ribbon.OkToRetryOnAllOperations=false 

4.對指定的http狀態碼進行重試

  1. serviceC.retryableStatusCodes=404,408,502,500 

坑八:hystrix超時

如下圖:

hystrix默認不開啟,但是如果開啟了hystrix,因為hystrix是在Ribbon外面,所以超時時間需要符合下面規則:hystrix超時 >= (MaxAutoRetries + 1) * (ribbon ConnectTimeout + ribbon ReadTimeout)

如果Ribbon不重試,MaxAutoRetries=0

根據上面公式,假如我們配置熔斷超時時間如下:

  1. hystrix.command.ServiceCClient#interface5(param).execution.isolation.thread.timeoutInMilliseconds=15000 
  2. ribbon.ReadTimeout=8000 

這個配置是不會重試一次的。serviceA調用serviceB時,hystrix會等待Ribbon返回的結果,如果Ribbon配置了重試,hystrix會一直等待直到超時。上面的配置,因為第一次請求已經耗去了8s,剩下時間7s不夠請求一次了,所以是不會進行重試的。

坑九:使用OpenFeign做http客戶端

即使不用注冊中心,使用OpenFeign做普通http客戶端也是很方便的,但是有三點需要注意:

  • 不用配置ribbon相關參數
  • 使用RestTemplate調用時,不考慮負載均衡
  • 使用過程中OpenFeign要組裝出自己的一套請求,跟直接使用http客戶端比,會有一定開銷
  • 使用OpenFeign有很多配置上的坑,對于沒有注冊中心的情況,建議直接使用http客戶端

 

責任編輯:武曉燕 來源: 程序員jinjunzhu
相關推薦

2021-04-09 08:13:14

API網關互聯網

2018-12-20 14:28:45

程序員開源支付系統

2020-02-09 16:52:02

睡醒公司倒閉

2020-04-10 10:15:29

算法開源Github

2020-06-12 11:03:22

Python開發工具

2021-02-09 09:50:21

SQLOracle應用

2021-07-16 07:57:35

SpringBootOpenFeign微服務

2025-04-17 08:10:41

2020-10-13 13:12:44

業務分析分析專家技能

2018-11-19 15:06:23

Python算法

2017-05-23 15:00:06

PythonDjangoadmin

2018-10-25 15:04:22

編程程序員陷阱

2017-03-31 09:35:14

Android函數Android庫

2017-12-15 10:50:40

Kotlin語法糖程序員

2021-04-19 17:12:53

網站工具

2020-10-27 12:06:17

MathJavaScript對象

2018-01-17 22:17:16

IT架構數據糟糕架構

2018-05-07 16:03:55

工單開源跟蹤系統

2013-04-23 09:49:43

負載測試最佳負載負載

2018-11-11 10:59:38

UI設計師背景界面
點贊
收藏

51CTO技術棧公眾號

主站蜘蛛池模板: 色爱综合网 | 一区二区在线免费观看视频 | 在线日韩av电影 | 日日草夜夜草 | 美女一级黄 | 成人h视频在线 | 精品少妇v888av | 国产精品免费一区二区三区四区 | 婷婷久久精品一区二区 | 国产一区二区三区在线视频 | 国产一区二区三区免费观看在线 | 国产 欧美 日韩 一区 | 久久久精品视 | 美女三区| 成人免费视频网站在线看 | 欧美涩| 91精品国产综合久久久久久丝袜 | 国产黄色在线观看 | 日韩中文字幕视频在线观看 | 99re6热在线精品视频播放 | 久久不卡 | 亚洲一区二区三区在线 | 激情自拍偷拍 | 日本福利片 | 福利片在线观看 | 欧美一级全黄 | 国产小视频在线 | 亚洲一区二区三区免费在线观看 | 日韩成人精品视频 | 影音先锋中文字幕在线观看 | 日本成人中文字幕 | 欧美日韩精品一区 | 成人乱人乱一区二区三区软件 | 国产成人综合一区二区三区 | 免费国产精品久久久久久 | 97国产精品视频人人做人人爱 | 国产精品不卡视频 | 三级免费 | 亚洲欧美国产毛片在线 | 亚洲三区在线观看 | 久久天天躁狠狠躁夜夜躁2014 |