【夯實Spring Cloud】Spring Cloud中使用Ribbon實現負載均衡詳解(上)

本文屬於【夯實Spring Cloud】系列文章,該系列旨在用通俗易懂的語言,帶大家瞭解和學習Spring Cloud技術,希望能給讀者帶來一些乾貨。系列目錄如下:

【夯實Spring Cloud】Dubbo沉睡5年,Spring Cloud開始崛起!
【夯實Spring Cloud】Spring Cloud中基於maven的分佈式項目框架的搭建
【夯實Spring Cloud】Spring Cloud中的Eureka服務註冊與發現詳解
【夯實Spring Cloud】Spring Cloud中如何完善Eureka中的服務信息
【夯實Spring Cloud】Spring Cloud中使用Eureka集羣搭建高可用服務註冊中心
【夯實Spring Cloud】Spring Cloud中的Eureka和Zookeeper的區別在哪?
【夯實Spring Cloud】Spring Cloud中使用Ribbon實現負載均衡詳解(上)
【夯實Spring Cloud】Spring Cloud中使用Ribbon實現負載均衡詳解(下)(正在寫……)
【夯實Spring Cloud】Spring Cloud中自定義Ribbon負載均衡策略(正在寫……)
【夯實Spring Cloud】Spring Cloud中使用Feign實現負載均衡詳解(正在寫……)
【夯實Srping Cloud】Spring Cloud中使用Hystrix實現斷路器原理詳解(正在寫……)
【夯實Spring Cloud】Spring Cloud中使用Zuul實現路由網關詳解(正在寫……)
【夯實Spring Cloud】Spring Cloud分佈式配置中心詳解(正在寫……)
【夯實Spring Cloud】未完待續


前面幾節主要介紹了 Spring Cloud 中的 Eureka 服務註冊與發現,這一篇文章主要介紹一下Spring Cloud Ribbon,什麼是 Ribbon 呢?首先看一下 Ribbon 的相關介紹。

1. 什麼是 Ribbon

Spring Cloud Ribbon 是一套實現客戶端負載均衡的工具。注意是客戶端,當然也有服務端的負載均衡工具,我們後面再介紹。可以認爲 Ribbon 就是一個負載均衡器(Load Balancer,簡稱LB,即:low比~~)。負載均衡就是將用戶的請求平攤的分配到多個服務上,從而達到系統的高可用。

簡單來說,Ribbon 的主要功能是提供客戶端的軟件負載均衡算法,將 Netflix 的中間層服務連接在一起。Ribbon 客戶端組件給我們提供了一套很完善的配置項,比如可以配置連接超時、重試等等。

再說的通俗一點,就是可以在配置文件中列出 LB 後面所有的機器(即服務),Ribbon 會自動根據某種規則(如輪詢、隨機等等)去連接這些機器(即服務),我們也可以自定義一些負載均衡算法。

再簡單點,Ribbon 就是一個類庫,集成在服務消費方,消費方從服務註冊中心獲知有哪些地址(即服務)可用,然後消費方通過 Ribbon 從這些地址當中選擇一個合適的服務器來消費服務。

更多資料可以觀看官方github:https://github.com/Netflix/ribbon

2. Ribbon的使用

我們在前面文章中,將訂單服務註冊到 Eureka,然後消費方可以通過 http 請求去獲取訂單的信息,但是這是最原始的 http 調用,沒有任何 Ribbon 的東西在裏面,接下來我們要在消費方(即microservice-order-consumer)植入 Ribbon。

2.1 導入 Ribbon 依賴

我們使用的Spring Cloud 版本是 Finchley,該版本需要導入的依賴如下:

<!--eureka Client-->
<dependency>
    <groupId>org.springframework.cloud</groupId>
    <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>
<!--ribbon負載均衡依賴-->
<dependency>
    <groupId>org.springframework.cloud</groupId>
    <artifactId>spring-cloud-starter-netflix-ribbon</artifactId>
</dependency>

可以看到,Eureka Client 的依賴也需要導入,因爲服務註冊到了 Eureka,Ribbon 也需要和 Eureka 整合,所以在消費方也導入了 Eureka 依賴。

2.2 配置 application.yml

server:
  port: 9001

eureka:
  client:
    register-with-eureka: false
    service-url:
      defaultZone: http://eureka01:7001/eureka/,http://eureka02:7002/eureka/,http://eureka03:7003/eureka/

由前面的內容(Spring Cloud中使用Eureka集羣搭建高可用服務註冊中心)可知,我們搭建了一個 Eureka 集羣,那麼就用這個集羣,這個消費方我們設置不註冊到該集羣中。

2.3 向 http 中植入 Ribbon

這是什麼意思呢?之前的 microservice-order-consumer 中是使用 RestTemplate 來發送 http 請求,調用訂單服務的,但是沒有負載均衡,所以現在我們要讓這個 http 調用自帶負載均衡。

即修改下 RestTemplate 配置:

/**
 * 配置RestTemplate
 * @author shengwu ni
 */
@Configuration
public class RestTemplateConfig {

    /**
     * '@LoadBalanced'註解表示使用Ribbon實現客戶端負載均衡
     * @return RestTemplate
     */
    @Bean
    @LoadBalanced
    public RestTemplate getRestTemplate() {
        return new RestTemplate();
    }
}

在方法上添加一個 @LoadBalanced 註解即可開啓 Ribbon 負載均衡。這樣就可以通過微服務的名字從 Eureka 中找到對應的服務並訪問了。

友情提示:別忘了在主啓動類上添加 @EnableEurekaClient,因爲這個消費方也是一個 Eureka Client,剛剛我們已經導入了 Eureka Client 的依賴了。

2.4 將ip改成服務名稱

剛剛提到了,開啓 Ribbon 負載均衡後,就可以通過微服務的名字從 Eureka 中找到對應的服務。我們先來看下原來是怎麼實現的。

/**
 * 訂單消費服務
 * @author shengwu ni
 */
@RestController
@RequestMapping("/consumer/order")
public class OrderConsumerController {

    /**
     * 訂單服務提供者模塊的 url 前綴
     */
//    private static final String ORDER_PROVIDER_URL_PREFIX = "http://localhost:8001";
    private static final String ORDER_PROVIDER_URL_PREFIX = "http://MICROSERVICE-ORDER";

    @Resource
    private RestTemplate restTemplate;

    @GetMapping("/get/{id}")
    public TOrder getOrder(@PathVariable Long id) {

        return restTemplate.getForObject(ORDER_PROVIDER_URL_PREFIX + "/provider/order/get/" + id, TOrder.class);
    }
}    

可以看出,註釋掉的那部分,是原來的訪問方式,訂單提供服務是8001端口,現在我們將ip+端口號這種訪問方式,改成微服務名稱,這個名稱就是 Eureka 管理界面顯示的註冊進去的名稱,也即服務提供方的application.yml配置文件中配置的服務名稱:

spring:
  application:
    name: microservice-order # 對外暴露的服務名稱

在前面文章中已經說了,不再贅述。

2.5 啓動服務,測試

還是和前面集羣文章中提到的一樣,分別啓動 eureka7001、eureka7002、eureka7003以及訂單服務8001,可以看到訂單服務已經註冊到 Eureka 集羣。

然後啓動消費方服務(microservice-order-consumer),然後在瀏覽器輸入 http://localhost:9001/consumer/order/get/1 即可查詢到對應的訂單服務:

{"id":1,"name":"跟武哥一起學 Spring Boot","price":39.99,"dbSource":"microservice01"}

說明,我們通過訂單的服務名稱即可獲取訂單信息了。可能到這裏,讀者還不明白我整了一大波,到最後就爲了通過服務名稱去獲取服務提供的信息嗎?

是的,這只是第一步,因爲在很多微服務中,你不可能去通過每個 ip 和端口號來找對應的服務,更何況,還有 Ribbon 負載均衡還沒上場呢?同一個微服務名稱,可以有多個服務,而 Ribbon 只需要通過服務名去獲取服務信息,至於獲取到的是哪一個?就看具體的負載均衡策略了,目前測試的 MICROSERVICE-ORDER 服務就一個提供者,所以不能體現出負載均衡。由於篇幅原因,下篇文章繼續。


源碼下載地址:https://gitee.com/eson15/springcloud_study
更多優質文章請關注我的微信公衆號【程序員私房菜】,回覆“資源”和“架構”可以領取優質的視頻學習資源。

程序員私房菜

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章