3.OpenFeign的使用

OpenFeign

文章目錄

  • OpenFeign
    • 一. 什么是OpenFeign
    • 二. OpenFeign基礎使用
      • 1.添加依賴
      • 2.配置Nacos配置信息
      • 3.在項目中開啟OpenFeign
      • 4.編寫OpenFeign調用代碼
      • 5.調用OpenFeign接口
    • 三. OpenFeign內置的超時重試機制
      • 1.配置超時重試
      • 2.覆蓋Retryer對象
    • 四.自定義超時重試機制
      • 1.自定義超時重試類
      • 2.設置配置文件
    • 五.OpenFeign超時重試底層實現
      • 1.超時重試底層實現

一. 什么是OpenFeign

OpenFeign的全稱為Spring Cloud OpenFeign,是Spring Cloud 開發的一款基于Feign的框架,聲明式Web服務客戶端。

Feign 是Netflix開源的一個聲明式的Web服務客戶端,它簡化了基于HTTP的服務調用,使得服務間的通信變得更加簡單和靈活。Feign通過定義接口、注解和動態代理等方式,將服務調用的過程封裝起來,開發者只需定義服務接口,而無需關心底層的HTTP請求和序列化等細節。

OpenFeign功能升級

OpenFeign在Feign的基礎上提供了以下增強和擴展功能:

  1. 更好的集成Spring Cloud組件:OpenFeign與Spring Cloud其他組件緊密集成,可以無縫地與其他Spring Cloud組件一起使用。
  2. 支持@FeignClient注解:OpenFeign引入了@FeignClient注解作為Feign客戶端的標識,可以方便地定義和使用遠程服務的聲明式接口。
  3. 錯誤處理改進:OpenFeign對異常的處理做了增強,提供了更好的錯誤信息和異常處理機制,使得開發者可以更方便地進行錯誤處理。
  4. 更豐富的配置項:OpenFeign提供了豐富的配置選項,可以對Feign客戶端的行為進行靈活的配置,例如超時設置、重試策略等。

二. OpenFeign基礎使用

OpenFeign通常要配合注冊中心一起使用,并且新版本OpenFeign也必須和負載均衡器一起使用,使用步驟如下:

  1. 添加依賴(Nacos注冊中心、OpenFeign、Spring Cloud LoadBalancer)
  2. 配置Nacos服務端信息
  3. 在項目中開啟OpenFeign
  4. 編寫OpenFeign調用代碼
  5. 編寫代碼通過OpenFeign調用生產者

1.添加依賴

<dependency><groupId>com.alibaba.cloud</groupId><artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>
<dependency><groupId>org.springframework.cloud</groupId><artifactId>spring-cloud-starter-loadbalancer</artifactId>
</dependency>
<dependency><groupId>org.springframework.cloud</groupId><artifactId>spring-cloud-starter-openfeign</artifactId>
</dependency>

2.配置Nacos配置信息

spring:application:name: nacos-consumer-democloud:nacos:discovery:server-addr: localhost:8848username: nacospassword: nacosregister-enabled: false # 消費者(不需要注冊到nacos中)

3.在項目中開啟OpenFeign

在啟動類文件中添加@EnableFeignClients注解即可

4.編寫OpenFeign調用代碼

@Service
@FeignClient("nacos-discovery") // 表示調用 nacos 中的 nacos-discovery 服務
public interface UserService {@RequestMapping("/user/getnamebyid") // 調用生產者的"/user/getnamebyid"接口public String getNameById(@RequestParam("id") int id);}

5.調用OpenFeign接口

@RestController
public class BusinessController {@Autowiredprivate UserService userService;@RequestMapping("/getnamebyid")public String getNameById(Integer id){System.out.println("------- do provider getNameById method" +LocalDateTime.now());return userService.getNameById(id);}}

三. OpenFeign內置的超時重試機制

在微服務架構中,服務之間是通過網絡進行通信的,而網絡是復雜和不穩定的,所以在調用服務時可能會失敗或超時,那么在這種情況下,就需要給OpenFeign配置超時重試機制。

什么是超時重試?

超時重試是一種在網絡通信中常用發的策略,用于處理請求在一定時間內未能得到響應的情況。當發起請求后,如果規定時間內沒有得到預期的響應,就會觸發超時重試機制,重新發送請求。

超時重試的主要目的是提高請求的可靠性和穩定性,以應對網絡的不穩定、服務不可用、響應延遲等不確定因素。

OpenFeign默認是不自動開啟超時重試

開啟有以下步驟:

  1. 配置超時重試
  2. 覆蓋Retryer對象

1.配置超時重試

spring:cloud:    openfeign:client:config:default:connect-timeout: 1000 #連接超時時間read-timeout: 1000 #讀取超時時間

2.覆蓋Retryer對象

@Configuration
public class RetryerConfig {@Beanpublic Retryer retryer(){return new Retryer.Default(1000,//重試間隔時間1000,//最大重試間隔時間3);//最大重試次數}
}

最大重試次數為3次,最大重試間隔時間是1秒,重試間隔時間是1秒

這時我們啟動一個實例,并設置保護閾值為0,啟動消費者。

訪問服務

image-20231122192057049

此時服務無法訪問,并觸發了超時重試機制,這時打開生產者者的控制臺:

image-20231122192120760

在控制臺我們可以看到總共打印了3次日志,因為我們設置的最大重試次數是3

為什么不是4次呢?

為什么不是4次?

因為Retryer的Default方法的源碼中重試次數變量attempt是從1開始的,然后核心方法continueOrPropagate中的if判斷是當this.attempt++ >= this.maxAttempts 時,才拋出異常。

image-20231122192856630

image-20231122192739555

四.自定義超時重試機制

自定義超時重試機制實現為以下兩步:

  1. 自定義超時重試類(實現Retryer接口,并重寫continueOrPropagate方法)
  2. 設置配置文件

1.自定義超時重試類

常見的超時重試策略有以下三種:

  1. 固定間隔重試:每次重試之間的時間間隔固定不變。
  2. 指數間隔重試:每次重試之間的時間間隔按指數遞增。
  3. 隨機間隔重試:每次重試之間的時間間隔是隨機的。
public class CustomRetryer implements Retryer {private final int maxAttempts; //最大嘗試次數private final long backoff;   //重試間隔時間int attempt;  //當前重試次數public CustomRetryer() {this.maxAttempts=3;this.backoff =1000;this.attempt=0;}public CustomRetryer(int maxAttempts, long backoff) {this.maxAttempts = maxAttempts;this.backoff = backoff;this.attempt=0;}@Overridepublic void continueOrPropagate(RetryableException e) {if (attempt++>=maxAttempts){throw e;}long interval = this.backoff;//重試間隔時間System.out.println(LocalDateTime.now()+" | 執行一次重試:"+interval);try {//重試間隔實際Thread.sleep(interval*attempt);} catch (InterruptedException ex) {ex.printStackTrace();}}@Overridepublic Retryer clone() {return  new CustomRetryer(maxAttempts,backoff);}
}

2.設置配置文件

spring:cloud:openfeign:client:config:default:connect-timeout: 1000 #連接超時時間read-timeout: 1000 #讀取超時時間retryer: com.example.consumer.config.CustomRetryer #自定義失敗重試類

啟動生產者和消費者服務,并嘗試調用服務,并查看控制臺

image-20231122221125671

  1. 這里我們設定的重試次數是3,但為什么會打印4次呢?

    是因為在自定義重試類中的attempt變量是從0開始的。

  2. 觀察日志文檔的時間間隔:從2s->3s->4s,最初attempt為1,1*1+read-timeout的1s所以是2s,然后1*1+read-timeout,以此類推……

五.OpenFeign超時重試底層實現

首先我們先了解以下OpenFeign的底層實現邏輯

在這里插入圖片描述

  1. 加注解:在啟動類或配置類上添加 @EnableFeignClients注解
  2. 動態代理:這個注解會觸發Spring框架的自動配置機制,掃描所有標記的@FeignClient的接口,并為它們創建代理實例。
  3. RequestTemplate發送HTTP請求:OpenFeign不能直接發送HTTP請求,它在動態代理里面將注解的路由地址拿出來,然后就能拼出來一個URL請求地址,然后再使用RequestTemplate去發送HTTP請求。
  4. RestTemplate依靠HTTP框架實現web請求:RestTemplate只是一個模板方法類,它只是規定了一個調用的API,底層并沒有實現,依靠的是HTTP框架實現的web請求(Apache 的HttpClient框架)

1.超時重試底層實現

OpenFeign超時的底層實現是通過配置底層的HTTP客戶端來實現的。OpenFeign允許在請求連接和讀取數據階段設置超時時間,具體超時配置可以通過HTTP客戶端的連接超時(connectTimeout)和讀取超時(readTimeout)來實現,可以在配置文件中設置超時參數。

OpenFeign重試的底層可通過觀察源碼來了解,它的源碼在SynchronousMethodHandler的invoke方法下,如下所示:

public Object invoke(Object[] argv) throws Throwable {RequestTemplate template = this.buildTemplateFromArgs.create(argv);Request.Options options = this.findOptions(argv);Retryer retryer = this.retryer.clone();// 死循環,如果成功或者重試結束就返回(通過throw終止while循環)while(true) {try {//通過HTTP Client發起通信return this.executeAndDecode(template, options);} catch (RetryableException var9) {RetryableException e = var9;//判斷是否重試try {retryer.continueOrPropagate(e);} catch (RetryableException var8) {Throwable cause = var8.getCause();if (this.propagationPolicy == ExceptionPropagationPolicy.UNWRAP && cause != null) {throw cause;}throw var8;}if (this.logLevel != Level.NONE) {this.logger.logRetry(this.metadata.configKey(), this.logLevel);}}}
}

因此OpenFeign的重試功能是通過其內置的Retryer組件和底層的HTTP客戶端實現的。

Retryer組件提供了重試策略的邏輯實現,而遠程接口則通過HTTP客戶端來完成調用。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/162724.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/162724.shtml
英文地址,請注明出處:http://en.pswp.cn/news/162724.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

Hive中常出現的錯誤(不定時更新)

1.加載數據失敗 hive> load data local inpath /home/user/hive.txt into table studentl> ; FAILED: SemanticException [Error 10001]: Line 1:56 Table not found studentl hive> load data local inpath /home/user/hive.txt into table student; Loading data to…

技術分享| anyRTC之RTN網絡

RTN(Real-time Network)中文名&#xff1a;實時音視頻傳輸網絡。 RTN是最近幾年由各大RTC的云廠商提出的一個全新架構的音視頻實時傳輸網絡概念。類似于直播的CDN網絡&#xff0c;RTN是對音視頻的實時性又強烈要求的場景而設計的&#xff0c;原理上全球端到端的時延通過RTN網絡…

JSP EL表達式獲取list/Map集合與java Bean對象

上文 JSP EL表達式基本使用 中 我們對EL表達式做了一個基本的了解 也做了基礎的字符串數據使用 那么 我們可以來看一下我們的集合 首先 list 這個比較簡單 我們直接這樣寫代碼 <% page import"java.util.ArrayList" %> <% page import"java.util.Lis…

基于C#實現優先隊列

一、堆結構 1.1性質 堆是一種很松散的序結構樹&#xff0c;只保存了父節點和孩子節點的大小關系&#xff0c;并不規定左右孩子的大小&#xff0c;不像排序樹那樣嚴格&#xff0c;又因為堆是一種完全二叉樹&#xff0c;設節點為 i,則 i/2 是 i 的父節點&#xff0c;2i 是 i 的…

安卓開發之HTTP API服務接口設計(基于okhttp3請求)

安卓中的請求 OkHttp3 是一個開源的 Java/Android HTTP 客戶端庫,由 Square 公司開發。它提供了簡潔和高效 的 API ,用于進行 HTTP 請求、處理響應以及與服務器進行通信。 以下是 OkHttp3 的一些主要特點和功能: 簡單易用: OkHttp3 提供了簡潔的 API ,使得發送 HTTP 請求變…

信息系統的安全保護等級的五個級別

信息系統的安全保護等級分為五級&#xff1a;第一級為自主保護級、第二級為指導保護級、第三級為監督保護級、第四級為強制保護級、第五級為專控保護級。 法律依據&#xff1a;《信息安全等級保護管理辦法》第四條 信息系統的安全保護等級分為以下五級&#xff1a;   &#…

【C語言】計算實時太陽角度(高度角、方位角),以及使用stm32單片機實時獲取時間戳

整體計算方法 在編寫該代碼的過程中尋找了多篇博文和論文&#xff0c;綜合所有文章且按網上的以0時的方位角的0&#xff0c;且隨時間累加累加至360度。我修改了博文和論文的一些角度的計算方法。得到一下代碼與網站計算的方位角相互驗證過&#xff0c;誤差不超過1 驗證網站 太…

LoRaWAN 中國地區文件詳細解讀

目錄 一、LoRaWAN簡介 二、CN470-510地區參數分析 1.信道頻率 2.支持功率 3.支持空速 4.最大負載大小 5.接受窗口參數 三、CN470_510默認參數 Lora LoraWAN教程 一、LoRaWAN簡介 LoraWAN是一種基于LoRa遠距離通信技術配套設計的一套通訊協議和系統架構。LoRaWAN網絡通…

Java實現拼圖游戲

1、了解拼圖游戲基本功能&#xff1a; 拼圖游戲內容由若干小圖像塊組成的&#xff0c;通過鼠標點擊圖像塊上下左右移動&#xff0c;完成圖像的拼湊。 2、拼圖游戲交互界面設計與開發&#xff1a; 通過創建窗體類、菜單、中間面板和左右面板完成設計拼圖的交互界面 &#xff…

外貿自建站服務器怎么選?網站搭建的工具?

外貿自建站服務器用哪個好&#xff1f;如何選海洋建站的服務器&#xff1f; 外貿自建站是企業拓展海外市場的重要手段之一。而在這個過程中&#xff0c;選擇一個適合的服務器對于網站的穩定運行和優化至關重要。海洋建站將為您介紹如何選擇適合的外貿自建站服務器。 外貿自建…

CSDN如何完整轉載別人的文章并做自己的筆記

1、這篇文章介紹主體的轉載&#xff08;粘貼&#xff09;方法&#xff1a; 轉載&#xff1a;CSDN快速轉載文章方法&#xff08;簡單&#xff09;_csdn轉載_biggolden1的博客-CSDN博客 2、這篇文章解決&#xff0c;對于含有代碼塊的文章粘貼后&#xff0c;出現的額外行號塊問題…

【STM32外設系列】GPS定位模塊(ATGM336H)

&#x1f380; 文章作者&#xff1a;二土電子 &#x1f338; 關注公眾號獲取更多資料&#xff01; &#x1f438; 期待大家一起學習交流&#xff01; 文章目錄 一、GPS模塊簡介二、使用方法2.1 引腳介紹2.2 數據幀介紹2.3 關于不同的啟動方式 三、前置知識3.1 strstr函數3.2…

DevSecOps 的未來

采用 可以做的事情還有很多。您編碼和構建的內容是您看到嵌入 CI/CD 管道的大部分進展的地方。隨著世界在不同的云環境中變得更加由 API 驅動&#xff0c;我們將考慮如何將安全角度嵌入到所有這些事物中&#xff0c;無論平臺如何構建。這是一個涉及人員的工作流程。您做得越多&…

基于H1ve一分鐘搭好CTF靶場

寫在前面 ? ? ? 上一篇文章給大家詳細介紹了基于H1ve搭建CTF靶場&#xff0c;以及過程中可能遇到的報錯及解決方法&#xff0c;那么這篇文章&#xff0c;我總結了一下&#xff0c;將不會遇到報錯的方法給到大家&#xff0c;但是前提是你的服務器最好是一個全新的哦~~~ 我…

Qt框架學習(1)

1.安裝Qt官網 2.Qt中的快捷鍵 快捷鍵解釋F4頭文件和實現文件切換ShiftF2變量:跳轉到聲明;函數:跳轉到定義;F5調試程序F3查找下一個CtrlShiftR修改所有選中的名稱F10單步(略過)調試,執行當前程序語句F11單步(跟蹤)調試,如果有函數則進入函數F9設置\取消斷點CtrlShiftS保存所有文…

C++基礎從0到1入門編程(四)類和對象

系統學習C 方便自己日后復習&#xff0c;錯誤的地方希望積極指正 往期文章&#xff1a; C基礎從0到1入門編程&#xff08;一&#xff09; C基礎從0到1入門編程&#xff08;二&#xff09; C基礎從0到1入門編程&#xff08;三&#xff09; 參考視頻&#xff1a; 1.黑馬程序員匠心…

Spring boot @Bean

Bean 是 Spring 框架中的一個注解&#xff0c;它的作用是將一個方法標記為 Spring 容器中的一個 Bean。具體來說&#xff0c;當你在一個類中使用 Bean 注解修飾一個方法時&#xff0c;這個方法將會在 Spring 容器中執行&#xff0c;并且返回的對象也會被 Spring 容器管理。 Be…

香蕉派BPI-M4 Zero單板計算機采用全志H618,板載2GRAM內存

Banana Pi BPI-M4 Zero 香蕉派 BPI-M4 Zero是BPI-M2 Zero的最新升級版本。它在性能上有很大的提高。主控芯片升級為全志科技H618 四核A53, CPU主頻提升25%。內存升級為2G LPDDR4&#xff0c;板載8G eMMC存儲。它支持5G WiFi 和藍牙, USB接口也升級為type-C。 它具有與樹莓派 …

23. 深度學習 - 多維向量自動求導

Hi, 你好。我是茶桁。 前面幾節課中&#xff0c;我們從最初的理解神經網絡&#xff0c;到講解函數&#xff0c;多層神經網絡&#xff0c;拓樸排序以及自動求導。 可以說&#xff0c;最難的部分已經過去了&#xff0c;這節課到了我們來收尾的階段&#xff0c;沒錯&#xff0c;生…

Android定位make有哪些target $ mgrep “build“ |grep target |grep image

環境 $ cat /proc/cpuinfo processor : 0 vendor_id : GenuineIntel cpu family : 6 model : 85 model name : Intel(R) Xeon(R) Gold 5122 CPU 3.60GHz stepping : 4 microcode : 0x2006e05 cpu MHz : 1200.086 cache…