使用FeignClient設置動態(tài)Url
FeignClient設置動態(tài)Url
1. 需求描述
一般情況下,微服務內(nèi)部調(diào)用都是通過注冊中心,eureka,zookeeper,nacos等實現(xiàn)動態(tài)調(diào)用,但是對于一些外部http調(diào)用,對于不在同一微服務內(nèi),不在同一注冊中心的服務調(diào)用,可以考慮SpringCloudOpenFeign,而且可以實現(xiàn)動態(tài)URL,通過參數(shù)動態(tài)控制。
2. 實現(xiàn)方案
服務端正常springboot項目,也不一定是springboot項目,只要正常提供RESTFul接口就可以,本次測試以springboot為例。主要是客戶端調(diào)用。
1.服務端:
/** ?* (Category)控制層 ?* ?* @author makejava ?* @since 2021-06-03 07:20:41 ?*/ @RestController @RequestMapping("/category") public class CategoryController { ? ? /** ? ? ?* 服務對象 ? ? ?*/ ? ? @Resource ? ? private CategoryService categoryService; ? ? /** ? ? ?* 測試服務 ? ? ?*/ ? ? @GetMapping("/test") ? ? public Response test() { ? ? ? ? return Response.createSuccessResponse("查詢成功", "我是測試服務"); ? ? } }
2.客戶端:
maven依賴
<dependency> ?? ?<groupId>org.springframework.cloud</groupId> ?? ?<artifactId>spring-cloud-starter-openfeign</artifactId> </dependency>
客戶端代碼
/** ?* 測試 ?* @author zrj ?* @since 2021-07-25 ?*/ @Api(value = "微盟鑒權(quán)測試") @RestController @RequestMapping("/weimob") public class ActivityController { ? ? @Resource ? ? private CategoryService categoryService; ? ? @GetMapping("/test") ? ? @ApiOperation(value = "微盟獲取Code") ? ? public Response test() throws URISyntaxException { ? ? ? ? System.out.println("-----測試-----"); ? ? ? ? URI uri = new URI("http://localhost:8080/category/test"); ? ? ? ? Response response = categoryService.test(uri); ? ? ? ? return Response.createSuccessResponse("查詢成功", response); ? ? } }
調(diào)用接口
/** ?* 測試接口Openfeign ?* @author zrj ?* @since 2021/7/25 ?**/ @Service("WeimobAuthorize") @FeignClient(url = "http://localhost:8080/category", name = "CategoryService") public interface CategoryService { ? ? @GetMapping ? ? Response test(URI uri); }
3. 細節(jié)分析
1.接口使用SpringMVC注解
接口方法的定義使用了SpringMVC的注解 @GetMapping、@RequestParam,其實SpringMVC的其他注解在此處都是支持的。(有其他文章提到也支持OpenFeign原有的注解@RequestLine、@Param等,但博主實測是不支持的,相關解析類為 feign.Contract,這個存疑)。
2.springcloud openfeign自動構(gòu)建實現(xiàn)類
在使用方式上,OpenFeign需要手動構(gòu)建代理對象,Spring Cloud OpenFeign 不同于 OpenFeign, Spring Cloud OpenFeign 幫我們自動生成了接口的代理對象(即實現(xiàn)類),并且注冊到Spring中,我們可以很方便的使用 @Autowired 注入代理對象然后使用。
其默認的代理對象是 LoadBalancerFeignClient。還有一個代理對象是 feign.Client.Default。
兩者區(qū)別在于:LoadBalancerFeignClient 通過服務名(下文提到)從Eureka查找相關的節(jié)點地址url,發(fā)起調(diào)用。feign.Client.Default 僅是簡單的直接調(diào)用。
3.FeignClient屬性name與URL一定要指定
@FeignClient(url = “http://localhost:8080/category”, name = “CategoryService”)
name
屬性,是@FeignClient 注解必要的,不定義時會報錯其默認指代Eureka上的服務名。
url
屬性,一定要指定,這是重點了! url屬性指定什么值其實不重要,因為最終都會被方法的URI參數(shù)值替換掉,它在這里另一個重要的作用,就是將接口的代理對象變成feign.Client.Default(上文提到默認是LoadBalancerFeignClient),這樣就繞過了從Eureka取節(jié)點地址這一步,畢竟第三方的地址不可能注冊到我們的Eureka上。(相關細節(jié)可自行debug FeignClientFactoryBean.getTarget())
FeignClient注解配置url屬性實現(xiàn)指定服務方
某天,跟同學聊天,同學說起之前面試的時候面試官提的一個問題:使用spring cloud,現(xiàn)在某個服務有一個新的接口需要驗證。該接口目前只上線了一臺機器,如何指定調(diào)用方只調(diào)用這臺機器。問題大致如此,可能有些出入??偨Y(jié)起來,就是希望能夠指定訪問某臺機器。這樣的情況,在我們平時也可能經(jīng)常遇到。比如甲乙兩人需要調(diào)試新接口,但注冊中心只有一個??赡苌厦嬗斜∥旒焊磷缘姆铡H绻覀儼凑漳J的輪詢的負載均衡規(guī)則去調(diào)用,七次調(diào)用才能輪到乙的服務,根本沒有辦法調(diào)試。所以這時候就需要我們能夠指定調(diào)用的服務方。
FeignClient注解通過配置url屬性可以指定調(diào)用的服務方。我們按照上面的例子,假設乙的IP為192.168.1.2,在端口8080上啟動的服務,那我們就可以把我們的url配置成http://192.168.1.2:8080。這樣調(diào)用的就一直是乙的服務了。
那我們配置了url和不配置url到底產(chǎn)生了哪些不同呢?
feign,或者說open-feign底層是使用,我以為默認是httpclient,但是我debug的結(jié)果是HttpURLConnection。知道為什么的可以留言告訴我。feign會基于配置,生成URI。當我們不配置url的時候,URI是這樣的http://service-name/path。使用FeignClien是LoadBalancerFeignClient,該類在處理該URI的時候會對服務名進行解析,也就是從注冊中心查詢該服務名下已經(jīng)注冊的服務器信息,包括IP和端口。然后將服務名替換成真實的鏈接。而當我們不配置url的時候,使用的FeignClient是Client的默認實現(xiàn)Default,該類就沒有解析的這一步而是直接通過HttpURLConnection進行請求。
以上為個人經(jīng)驗,希望能給大家一個參考,也希望大家多多支持腳本之家。
相關文章
SpringBoot 定制化返回數(shù)據(jù)的實現(xiàn)示例
這篇文章主要介紹了SpringBoot 定制化返回數(shù)據(jù)的實現(xiàn)示例,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧2020-07-07Spring注解@Qualifier的使用&&與@Primary注解的不同
今天帶你了解一下Spring框架中的@Qualifier?注解,它解決了哪些問題,以及如何使用它,我們還將了解它與?@Primary?注解的不同之處,感興趣的朋友跟隨小編一起看看吧2023-10-10Spring MVC+FastJson+Swagger集成的完整實例教程
這篇文章主要給大家分享介紹了關于Spring MVC+FastJson+Swagger集成的完整實例教程,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧。2018-04-04關于RedisTemplate之opsForValue的使用說明
這篇文章主要介紹了關于RedisTemplate之opsForValue的使用說明,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教2022-06-06Spring項目集成RabbitMQ及自動創(chuàng)建隊列
這篇文章主要介紹了Spring項目集成RabbitMQ及自動創(chuàng)建隊列,本文內(nèi)容分別在Spring(V5.2.6)和Spring Boot(V2.5.14)兩個項目中經(jīng)過了驗證,需要的朋友可以參考下2024-02-02