?【Alibaba中介軟體技術系列】「Nacos技術專題」服務註冊與發現相關的原理分析

浩宇天尚發表於2022-01-22

背景介紹

前幾篇文章介紹了Nacos配置中心服務的能力機制,接下來,我們來介紹Nacos另一個非常重要的特性就是服務註冊與發現,說到服務的註冊與發現相信大家應該都不陌生,在微服務盛行的今天,服務是非常重要的,而在 Nacos 中服務更被稱為他的一等公民。Nacos 支援幾乎所有主流型別的 “服務” 的發現、配置和管理。

服務 (Service)

服務是指一個或一組軟體功能(例如特定資訊的檢索或一組操作的執行),其目的是不同的客戶端可以為不同的目的重用(例如通過跨程式的網路呼叫)。Nacos 支援主流的服務生態,如 Kubernetes Service、gRPC|Dubbo RPC Service 或者 Spring Cloud RESTful Service。

nacos的架構圖所示

(dubbo) RPC微服務的基礎架構

圖中的6個步驟的含義解釋如下:

  1. 服務容器負責啟動,載入,執行服務提供者。
  2. 服務提供者在啟動時,向註冊中心註冊自己提供的服務。
  3. 服務消費者在啟動時,向註冊中心訂閱自己所需的服務。
  4. 註冊中心返回服務提供者地址列表給消費者,如果有變更,註冊中心將基於長連線推送變更資料給消費者。
  5. 服務消費者,從提供者地址列表中,基於軟負載均衡演算法,選一臺提供者進行呼叫,如果呼叫失敗,再選另一臺呼叫。
  6. 服務消費者和提供者,在記憶體中累計呼叫次數和呼叫時間,定時每分鐘傳送一次統計資料到監控中心。

服務註冊中心 (Service Registry)

上圖中Registry就是註冊中心,負責服務的註冊與發現,Dubbo服務體系之前使用Zookeeper或者自己的Registry 實現,而 Nacos 則是另一種 Registry的實現。

服務註冊中心,它是服務,其例項及後設資料的資料庫(Dubbo3已經將源資料中心、配置服務全部提取獨立出來了),服務例項在啟動時註冊到服務登錄檔,並在關閉時登出。

服務和路由器的客戶端查詢服務登錄檔以查詢服務的可用例項,服務註冊中心可能會呼叫服務例項的健康檢查 API 來驗證它是否能夠處理請求。

服務後設資料 (Service Metadata)

服務後設資料是指包括服務端點(endpoints)、服務標籤、服務版本號、服務例項權重、路由規則、安全策略等描述服務的資料。

邏輯架構及其元件介紹

  • 服務管理:實現服務CRUD,域名CRUD,服務健康狀態檢查,服務權重管理等功能
  • 配置管理:實現配置管CRUD,版本管理,灰度管理,監聽管理,推送軌跡,聚合資料等功能
  • 後設資料管理:提供後設資料CURD 和打標能力
  • 外掛機制:實現三個模組可分可合能力,實現擴充套件點SPI機制
  • 事件機制:實現非同步化事件通知,sdk資料變化非同步通知等邏輯
  • 日誌模組:管理日誌分類,日誌級別,日誌可移植性(尤其避免衝突),日誌格式,異常碼+幫助文件
  • 回撥機制:sdk通知資料,通過統一的模式回撥使用者處理。介面和資料結構需要具備可擴充套件性
  • 定址模式:解決ip,域名,nameserver、廣播等多種定址模式,需要可擴充套件
  • 推送通道:解決server與儲存、server間、server與sdk間推送效能問題
  • 容量管理:管理每個租戶,分組下的容量,防止儲存被寫爆,影響服務可用性
  • 流量管理:按照租戶,分組等多個維度對請求頻率,長連結個數,報文大小,請求流控進行控制
  • 快取機制:容災目錄,本地快取,server快取機制。容災目錄使用需要工具
  • 啟動模式:按照單機模式,配置模式,服務模式,dns模式,或者all模式,啟動不同的程式+UI
  • 一致性協議:解決不同資料,不同一致性要求情況下,不同一致性機制
  • 儲存模組:解決資料持久化、非持久化儲存,解決資料分片問題
  • Nameserver:解決namespace到clusterid的路由問題,解決使用者環境與nacos物理環境對映問題
  • CMDB:解決後設資料儲存,與三方cmdb系統對接問題,解決應用,人,資源關係
  • Metrics:暴露標準metrics資料,方便與三方監控系統打通
  • Trace:暴露標準trace,方便與SLA系統打通,日誌白平化,推送軌跡等能力,並且可以和計量計費系統打通
  • 接入管理:相當於阿里雲開通服務,分配身份、容量、許可權過程
  • 使用者管理:解決使用者管理,登入,sso等問題
  • 許可權管理:解決身份識別,訪問控制,角色管理等問題
  • 審計系統:擴充套件介面方便與不同公司審計系統打通
  • 通知系統:核心資料變更,或者操作,方便通過SMS系統打通,通知到對應人資料變更
  • OpenAPI:暴露標準Rest風格HTTP介面,簡單易用,方便多語言整合
  • Console:易用控制檯,做服務管理、配置管理等操作
  • SDK:多語言sdk
  • Agent:dns-f類似模式,或者與mesh等方案整合
  • CLI:命令列對產品進行輕量化管理,像git一樣好用

Nacos 的服務註冊與發現

服務提供方 (Service Provider)

是指提供可複用和可呼叫服務的應用方。

模擬服務註冊

服務註冊最重要的就是將服務註冊到哪裡,在註冊中心服務端,肯定有一個用來管理服務的容器,他儲存著所有服務的例項。不需要知道該容器具體的實現細節,只需要知道有這樣一個概念。

  • 將同一個服務的兩個例項註冊到 Nacos 中:

  • 雙註冊模式注入進入

  • 維持服務線上狀態

demo程式碼如下:

通過 NamingService 介面的 registerInstance 方法就可以將服務進行註冊了,該方法有很多過載的方法,這裡我們選擇一個簡單的來呼叫就好了。註冊完成後,通過呼叫 getAllInstances 方法,立即獲取所有可用的例項,然後讓主執行緒等待,列印如下:

可以發現naming客戶端成功獲取到了兩個例項。

服務消費方 (Service Consumer)

服務註冊到註冊中心後,服務的消費者就可以進行服務發現的流程了,消費者可以直接向註冊中心傳送獲取某個服務例項的請求,這種情況下注冊中心將返回所有可用的服務例項給消費者,但是一般不推薦這種情況。另一種方法就是服務的消費者向註冊中心訂閱某個服務,並提交一個監聽器,當註冊中心中服務發生變更時,監聽器會收到通知,這時消費者更新本地的服務例項列表,以保證所有的服務均是可用的。

Nacos消費服務機制

是指會發起對某個服務呼叫的應用方。服務註冊之後,服務的消費者就可以向註冊中心訂閱自己所需要的服務了,註冊中心會將所有服務的例項“推送”給消費者,實際上獲取服務是客戶端主動輪詢的,跟客戶端獲取配置中心的配置項的原理一樣。

現在我建立一個服務消費者,然後向註冊中心訂閱一個服務,當接收到註冊中心返回的服務列表之後,執行5次 select 服務例項的操作,相當於進行一個模擬的服務請求,具體的程式碼如下圖所示:

其中的 printInstances 方法主要是列印出所有服務的例項,將 ServiceConsumer 類啟動之後,列印出如下的日誌:

Nacos機制負載均衡

負載均衡有很多中實現方式,包括輪詢法,隨機方法法,對請求ip做hash後取模等等,從負載的維度考慮又分為:服務端負載均衡和客戶端負載均衡。Nacos 的客戶端在獲取到服務的完整例項列表後,會在客戶端進行負載均衡演算法來獲取一個可用的例項,模式使用的是隨機獲取的方式。

Nacos 服務註冊與訂閱的完整流程

  • Nacos客戶端進行服務註冊有兩個部分組成,一個是將服務資訊註冊到服務端,另一個是像服務端傳送心跳包,這兩個操作都是通過NamingProxy 和服務端進行資料互動的。

  • Nacos客戶端進行服務訂閱時也有兩部分組成,一個是不斷從服務端查詢可用服務例項的定時任務,另一個是不斷從已變服務佇列中取出服務並通知 EventListener 持有者的定時任務,更新服務訂閱列表。

參考資料

https://nacos.io/zh-cn/docs/feature-list.html

相關文章