Spring Cloud 系列之 Bus 消息總線
1|0什麼是消息總線
消息代理中間件建構一個共用的消息主題讓所有微服務執行個體訂閱,當該消息主題産生消息時會被所有微服務執行個體監聽和消費。
消息代理又是什麼?消息代理是一個消息驗證、傳輸、路由的架構模式,主要用來實作接收和分發消息,并根據設定好的消息處理流來轉發給正确的應用。它在微服務之間起到通信排程作用,減少了服務之間的依賴。
2|0什麼是 Spring Cloud Bus
Spring Cloud Bus 是 Spring Cloud 體系内的消息總線,用來連接配接分布式系統的所有節點。
Spring Cloud Bus 将分布式的節點用輕量的消息代理(RibbitMQ、Kafka)連接配接起來。可以通過消息代理廣播配置檔案的更改,或服務之間的通訊,也可以用于監控。解決了微服務資料變更,及時同步的問題。
官方文檔:
https://cloud.spring.io/spring-cloud-static/spring-cloud-bus/2.2.1.RELEASE/reference/html/3|0什麼時候使用 Spring Cloud Bus
微服務一般都采用叢集方式部署,而且在高并發下經常需要對服務進行擴容、縮容、上線、下線的操作。比如我們需要更新配置,又或者需要同時失效所有伺服器上的某個緩存,需要向所有相關的伺服器發送指令,此時就可以選擇使用 Spring Cloud Bus 了。
總的來說,就是在我們需要把一個操作散發到所有後端相關伺服器的時候,就可以選擇使用 Spring Cloud Bus 了。
接下來我們通過 Spring Cloud Bus 實作微服務架構的配置重新整理。
4|0環境準備
RibbitMQ v3.8.2 位址:192.168.10.101
bus-demo 聚合工程。SpringBoot 2.2.4.RELEASE、Spring Cloud Hoxton.SR1。
eureka-server:注冊中心
eureka-server02:注冊中心
config-server:配置中心服務端
config-server02:配置中心服務端
order-service:訂單服務(配置中心用戶端)
order-service02:訂單服務(配置中心用戶端)
配置檔案 order-service-prod.yml
spring: application: name: order-service # 應用名稱 # 配置 Eureka Server 注冊中心 eureka: instance: prefer-ip-address: true # 是否使用 ip 位址注冊 instance-id: ${spring.cloud.client.ip-address}:${server.port} # ip:port client: service-url: # 設定服務注冊中心位址 defaultZone:
http://localhost:8761/eureka/,http://localhost:8762/eureka/# 自定義配置 name: order-service-prod password: root
5|0Spring Cloud Bus 實作配置重新整理
5|1用戶端發起通知
點選連結觀看:用戶端發起通知視訊(擷取更多請關注公衆号「哈喽沃德先生」)
消息總線(Bus)的典型應用場景就是配置中心用戶端重新整理。
我們在學習 Spring Cloud Config 配置中心時給大家講了基于 Actuator 的配置重新整理,當時的案例隻有一個 Config Client,我們可以使用 Webhook,設定手動重新整理都不算太費事,但是如果用戶端比較多的情況下,一個一個去手動重新整理未免有點複雜,這種方案就不太适合了。使用 Spring Cloud Bus 可以完美解決這一問題。
借助 Spring Cloud Bus 的廣播功能,讓 Config Client 都訂閱配置更新事件,當配置更新時,觸發其中一個端的更新事件,Spring Cloud Bus 就把此事件廣播到其他訂閱用戶端,以此來達到批量更新。
Webhook 監聽被觸發,給 ConfigClient A 發送 bus-refresh 請求重新整理配置
ConfigClient A 讀取 ConfigServer 中的配置,并且發送消息給 Bus
Bus 接收消息後廣播通知其他 ConfigClient
其他 ConfigClient 收到消息重新讀取最新配置
添加依賴
Config Client 添加 spring cloud starter bus amqp 依賴。
org.springframework.cloudspring-cloud-starter-bus-amqp
配置檔案
配置檔案需要配置 消息隊列 和 bus-refresh 自動重新整理端點。/actuator/bus-refresh 端點會清除 @RefreshScope緩存重新綁定屬性。
Config Client 的 bootstrap.yml 核心配置。
spring: cloud: config: name: order-service # 配置檔案名稱,對應 git 倉庫中配置檔案前半部分 label: master # git 分支 profile: prod # 指定環境 discovery: enabled: true # 開啟 service-id: config-server # 指定配置中心服務端的 service-id # 消息隊列 rabbitmq: host: 192.168.10.101 port: 5672 username: guest password: guest virtual-host: / # 度量名額監控與健康檢查 management: endpoints: web: base-path: /actuator # 通路端點根路徑,預設為 /actuator exposure: include: bus-refresh # 需要開啟的端點 #exclude: # 不需要開啟的端點
測試
檢視端點
通路:
http://localhost:9091/actuator 可以看到已經開啟了 bus-refresh 自動重新整理端點。 http://localhost:9091/name 和 http://localhost:9092/name結果如下:
修改 Git 倉庫配置
修改 Git 倉庫配置資訊如下:
自定義配置 name: order-service-prod-1.0
自動重新整理
重新整理頁面發現結果并未改變,沒事正常。
通過 Post 方式調用「任意用戶端」的自動重新整理端點:
http://localhost:9091/actuator/bus-refresh再次通路結果如下:
檢視隊列
再來觀察一下消息隊列的 UI 界面,發現多了一個 springCloudBus 的交換機。
該交換機下綁定了兩個隊列對應我們的兩個 Config Client。
用戶端發起通知缺陷
打破了微服務的職責單一性。微服務本身是業務子產品,它本不應該承擔配置重新整理的職責。
破壞了微服務各節點的對等性。
存在一定的局限性。例如,微服務在遷移時,它的網絡位址常常會發生變化,此時如果想要做到自動重新整理,就不得不修改Webhook 的配置。
5|2服務端發起通知
點選連結觀看:服務端發起通知視訊(擷取更多請關注公衆号「哈喽沃德先生」)
為了解決用戶端發起通知缺陷,我們改用服務端發起通知。
Webhook監聽被觸發,給 ConfigServer 發送 bus-refresh 請求重新整理配置
ConfigServer 發送消息給 Bus
Bus 接收消息後廣播通知所有 ConfigClient
各 ConfigClient 收到消息重新讀取最新配置
Config Server 添加 spring cloud starter bus amqp 依賴。
Config Server 的 application.yml 核心配置。
spring: application: name: config-server # 應用名稱 cloud: config: server: git: uri:
https://github.com/imrhelloworld/config-repo# 配置檔案所在倉庫位址 #username: # Github 等産品的登入賬号 #password: # Github 等産品的登入密碼 #default-label: master # 配置檔案分支 #search-paths: # 配置檔案所在根目錄 # 消息隊列 rabbitmq: host: 192.168.10.101 port: 5672 username: guest password: guest virtual-host: / # 配置 Eureka Server 注冊中心 eureka: instance: prefer-ip-address: true # 是否使用 ip 位址注冊 instance-id: ${spring.cloud.client.ip-address}:${server.port} # ip:port client: service-url: # 設定服務注冊中心位址 defaultZone:
# 度量名額監控與健康檢查 management: endpoints: web: base-path: /actuator # 通路端點根路徑,預設為 /actuator exposure: include: bus-refresh # 需要開啟的端點 #exclude: # 不需要開啟的端點
http://localhost:8888/actuator自定義配置 name: order-service-prod-2.0
通過 Post 方式調用「任意服務端」的自動重新整理端點:
http://localhost:8888/actuator/bus-refresh該交換機下綁定了四個隊列對應我們的兩個 Config Server 和兩個 Config Client。
5|3局部重新整理
假設有這樣一種場景,我們開發了一個新的功能,此時需要對該功能進行測試。我們隻希望其中一個微服務的配置被更新,等功能測試完畢,正式部署線上時再更新至整個叢集。但是由于所有微服務都受 Spring Cloud Bus 的控制,我們更新了其中一個微服務的配置,就會導緻其他服務也被通知去更新配置。這時候局部重新整理的作用就展現出來了。
重新整理指定服務
自定義配置 name: order-service-prod-3.0
http://localhost:8888/actuator/bus-refresh/order-service:90919091 端口的用戶端已經更新配置。
9092 端口的用戶端沒有更新配置。
重新整理指定叢集
假設現在功能測試完畢,需要正式部署線上更新至整個叢集。但是由于 Spring Cloud Bus 控制着多個微服務叢集(訂單微服務、商品微服務等),而我們隻想更新指定叢集下的配置,這個時候就可以使用 Bus 提供的通配符更新方案。
自定義配置 name: order-service-prod-4.0
http://localhost:8888/actuator/bus-refresh/order-service:** 再次通路結果如下:
至此 Bus 消息總線所有的知識點就講解結束了。
EOF
本文作者:哈喽沃德先生
本文連結:
https://www.cnblogs.com/mrhelloworld/p/bus.html