服務(wù)注冊(cè)中心架構(gòu)演進(jìn)

1. 概述

服務(wù)注冊(cè)中心(下稱注冊(cè)中心)是微服務(wù)架構(gòu)非常重要的一個(gè)組件,在微服務(wù)架構(gòu)里主要起到了協(xié)調(diào)者的一個(gè)作用。因?yàn)楦鱾€(gè)公司的架構(gòu)、規(guī)模、部署環(huán)境等等都不盡相同,所以在注冊(cè)中心在業(yè)界有很多不同的實(shí)踐,包括各種各樣的技術(shù)選型、層出不窮的技術(shù)改進(jìn)。

本文將從注冊(cè)中心的功能實(shí)現(xiàn)、功能擴(kuò)展、規(guī)模變大等實(shí)際情況出發(fā),結(jié)合現(xiàn)有的技術(shù)框架以及一些國內(nèi)外公司的技術(shù)實(shí)踐,來介紹下 筆者了解的 注冊(cè)中心的演進(jìn)。另外其它例如 DNS、組播等地址發(fā)現(xiàn)機(jī)制本文不展開討論,只討論注冊(cè)中心。

閱讀本文之前,我們先統(tǒng)一一下基本術(shù)語,對(duì)齊一下大家的理解。

名詞 解釋
注冊(cè)中心(Registry) 服務(wù)注冊(cè)中心,本文主要解釋的微服務(wù)組件。
注冊(cè)中心客戶端(Registry Client) 不管是服務(wù)提供者還是服務(wù)調(diào)用者,都算是注冊(cè)中心的客戶端,本文里簡稱客戶端。
注冊(cè)中心管理端(Registry Console) 注冊(cè)中心數(shù)據(jù)的管理端,本文里簡稱管理端 。
服務(wù)(Service) 一般是指一個(gè)接口,可以包括多個(gè)方法。例如訂單服務(wù)包含有查詢訂單、新增訂單等方法
服務(wù)提供者(Provider) 暴露一個(gè)監(jiān)聽端口,提供一到多個(gè)服務(wù)。
服務(wù)調(diào)用者(Consumer) 連接服務(wù)提供者的端口,發(fā)起遠(yuǎn)程調(diào)用。

2. 注冊(cè)中心功能

注冊(cè)中心與配置中心

很多人經(jīng)常把注冊(cè)中心和配置中心混為一談,一般這么認(rèn)為的因?yàn)榉?wù)注冊(cè)的數(shù)據(jù)其實(shí)就是配置的一種,其實(shí)這樣解釋也不無道理,的確注冊(cè)中心的數(shù)據(jù)是配置的一種。但是注冊(cè)中心之所以獨(dú)立的存在,那是因?yàn)樽?cè)中心的數(shù)據(jù)有一定的業(yè)務(wù)獨(dú)立性,一般都是為了描述微服務(wù)相關(guān)的。所以本文的觀點(diǎn)就是注冊(cè)中心完全不依賴配置中心,而是一個(gè)獨(dú)立的系統(tǒng)。

2.1 注冊(cè)中心需求

注冊(cè)中心一般包含如下幾個(gè)功能:

  1. 服務(wù)發(fā)現(xiàn):
    • 服務(wù)注冊(cè)/反注冊(cè):保存服務(wù)提供者和服務(wù)調(diào)用者的信息
    • 服務(wù)訂閱/取消訂閱:服務(wù)調(diào)用者訂閱服務(wù)提供者的信息,最好有實(shí)時(shí)推送的功能
    • 服務(wù)路由(可選):具有篩選整合服務(wù)提供者的能力。
  2. 服務(wù)配置(不包括其它無關(guān)配置):
    • 配置訂閱:服務(wù)提供者和服務(wù)調(diào)用者訂閱微服務(wù)相關(guān)的配置
    • 配置下發(fā)(可選):主動(dòng)將配置推送給服務(wù)提供者和服務(wù)調(diào)用者
  3. 服務(wù)健康檢測
    • 檢測服務(wù)提供者的健康情況

2.2 一致性分歧

這里不得不提一下,我們知道分布式里一個(gè)重要的理論,那就是 CAP。在注冊(cè)中心的發(fā)展上面,一直有兩個(gè)分支:一個(gè)就是 CP 系統(tǒng),追求數(shù)據(jù)的強(qiáng)一致性。還有一個(gè)是 AP 系統(tǒng),追求高可用與最終一致。

2.3 為什么不用DNS

DNS 只是到 IP 級(jí)別,無法處理端口等信息。DNS 攜帶的數(shù)據(jù)較少,例如節(jié)點(diǎn)權(quán)重、序列化方式等等,無法傳遞。另外 DNS 沒有節(jié)點(diǎn)狀態(tài)管理功能,如果由外部系統(tǒng)刷新,那么將無法剔除死的節(jié)點(diǎn)。

3 注冊(cè)中心發(fā)展階段

注冊(cè)中心的規(guī)模一定是隨著業(yè)務(wù)的發(fā)展而發(fā)展的,在不同的階段有不同的技術(shù)實(shí)現(xiàn)方案。注冊(cè)中心數(shù)據(jù)源一般會(huì)選擇文件存儲(chǔ),數(shù)據(jù)庫存儲(chǔ),KV存儲(chǔ)等等。

3.1 小型注冊(cè)中心

這個(gè)階段的注冊(cè)中心,一般最關(guān)心的肯定是服務(wù)發(fā)現(xiàn)這個(gè)特性,而且可能是一個(gè)很小的體量、很短的開發(fā)迭代周期、我們需要一個(gè)快速開發(fā)上手的環(huán)境。具體情況:

  1. 單數(shù)據(jù)中心
  2. 服務(wù)規(guī)模較?。航涌跀?shù)在 5K 以下,注冊(cè)中心客戶端數(shù)量在 50K 以下。

3.2 中型注冊(cè)中心

這個(gè)階段的注冊(cè)中心,架構(gòu)已經(jīng)非常復(fù)雜,涉及到跨機(jī)房容災(zāi)等特性。一般會(huì)有專門的技術(shù)團(tuán)隊(duì)來做注冊(cè)中心的日常運(yùn)維。具體情況:

  1. 多數(shù)據(jù)中心
  2. 服務(wù)規(guī)模較大:接口數(shù)在 20K 以下,注冊(cè)中心客戶端數(shù)量在200K以下。

3.3 大型注冊(cè)中心

這個(gè)階段的注冊(cè)中心,數(shù)據(jù)量已經(jīng)非常大,可能一個(gè)注冊(cè)中心已經(jīng)無法滿足需求,必須拆為多個(gè)注冊(cè)中心,甚至需要容量的無限擴(kuò)展。具體情況:

  1. 非常多的數(shù)據(jù)中心
  2. 服務(wù)規(guī)模十分大,單節(jié)點(diǎn)無法滿足全量存儲(chǔ)。

4. CP類注冊(cè)中心演進(jìn)

典型的有Zookeeper,Consul,etcd等。

階段一:注冊(cè)中心高可用
部署5個(gè)主節(jié)點(diǎn)(只是按經(jīng)驗(yàn)值舉例,3臺(tái)或者7臺(tái)都行),只要半數(shù)以上存活,其中一個(gè)會(huì)成為Leader。
客戶端隨機(jī)選擇一臺(tái)直接接入主節(jié)點(diǎn)。客戶端拿注冊(cè)中心的地址可以通過DNS或者其它地方動(dòng)態(tài)發(fā)現(xiàn)。
管理端從主節(jié)點(diǎn)的其中一臺(tái)讀取數(shù)據(jù)。

圖1:注冊(cè)中心高可用

階段二:注冊(cè)中心提高性能
此時(shí)如果讀取節(jié)點(diǎn)的數(shù)據(jù)量特別大的話,那么可能會(huì)影響性能,那么我們可以做一些讀寫分離的操作。
在5臺(tái)主節(jié)點(diǎn)之外,部署多臺(tái)Zookeeper Observer節(jié)點(diǎn)(可擴(kuò)展),客戶端接入Observer節(jié)點(diǎn)。
主節(jié)點(diǎn)不處理長連接請(qǐng)求。
管理端從某個(gè)Observer讀取數(shù)據(jù)。

圖2:注冊(cè)中心讀寫分離

Consul也有Consul Client節(jié)點(diǎn),類似Zookeeper的Observer節(jié)點(diǎn)

這樣的架構(gòu)作為小型注冊(cè)中心基本沒啥問題。

** 階段三:服務(wù)高可用**
通過Zookeeper的臨時(shí)節(jié)點(diǎn)可以實(shí)現(xiàn)狀態(tài)檢測,但是一般不是很推薦。因?yàn)樽?cè)中心和服務(wù)提供者斷開連接的時(shí)候,注冊(cè)中心其實(shí)是無法判斷服務(wù)提供者是服務(wù)異常還是只是網(wǎng)絡(luò)分區(qū),最好是有額外的輔助進(jìn)行判斷。
例如提供一組狀態(tài)檢測服務(wù),部署在機(jī)房的不同域(例如跨機(jī)架、跨交換機(jī)等,越分散越好),進(jìn)行一定的投票,如果半數(shù)以上認(rèn)為死了,則上報(bào)狀態(tài)給注冊(cè)中心。

圖3:服務(wù)高可用

** 階段四:跨機(jī)房容災(zāi)**
如果此時(shí)出現(xiàn)多個(gè)機(jī)房,還要做數(shù)據(jù)共享的話,那么一定需要三個(gè)及以上機(jī)房。下面的圖我就不畫多個(gè)節(jié)點(diǎn)了,Zookeeper以集群的圖展示。
每個(gè)機(jī)房部署相同的節(jié)點(diǎn),當(dāng)其中一個(gè)機(jī)房出現(xiàn)網(wǎng)絡(luò)分區(qū),那么剩下的兩個(gè)機(jī)房繼續(xù)可用。
狀態(tài)檢測服務(wù)只檢查自己同機(jī)房的節(jié)點(diǎn)。

圖4:單注冊(cè)中心跨機(jī)房容災(zāi)

** 階段5:跨機(jī)房數(shù)據(jù)訪問 **
假如每個(gè)機(jī)房之間的數(shù)據(jù)是獨(dú)立的,那么得部署獨(dú)立的注冊(cè)中心。
此時(shí)如果需要客戶端做與多個(gè)注冊(cè)中心連接,或者注冊(cè)中心之間自己做數(shù)據(jù)同步。
圖 5 展示的是,注冊(cè)中心直接的節(jié)點(diǎn)是獨(dú)立的不共享的,由客戶端進(jìn)行跨注冊(cè)中心數(shù)據(jù)訪問,在客戶端做數(shù)據(jù)聚合。


圖5:多注冊(cè)中心跨機(jī)房數(shù)據(jù)訪問

圖 6 展示的是,注冊(cè)中心直接的節(jié)點(diǎn)是獨(dú)立的,但是數(shù)據(jù)是共享的,由注冊(cè)中心直接做數(shù)據(jù)同步合并,客戶端無需處理。


圖6:多注冊(cè)中心跨機(jī)房數(shù)據(jù)同步

Consul 提供了個(gè)功能叫跨數(shù)據(jù)中心訪問,但是其實(shí)數(shù)據(jù)是分開存放的。例如 dc1 和 dc2,在網(wǎng)絡(luò)正常的情況下,dc1 可以訪問 dc2 的數(shù)據(jù);但是網(wǎng)絡(luò)斷開的時(shí)候,dc1 是無法訪問 dc2 的數(shù)據(jù),dc1 本地并沒有存放 dc2 的數(shù)據(jù)。可以通過第三方實(shí)現(xiàn)做數(shù)據(jù)同步,參考:consul-replicate

這樣的架構(gòu)作為中型注冊(cè)中心基本沒啥問題。

5. AP類注冊(cè)中心演進(jìn)

我們會(huì)選用一些數(shù)據(jù)源,例如DB、文件、KV存儲(chǔ)等,但是直接接入數(shù)據(jù)源的就不多見了,一般會(huì)有個(gè)自己實(shí)現(xiàn)的注冊(cè)中心。在下面的圖中,DB、文件、KV存儲(chǔ)我們統(tǒng)稱“Datasouce(數(shù)據(jù)源)”。

** 階段一:注冊(cè)中心高可用 **

圖 7 我們采用數(shù)據(jù)庫主備或者是 Redis 集群作為一個(gè)統(tǒng)一的數(shù)據(jù)源,然后開發(fā) Registry Proxy 程序(以下簡稱注冊(cè)中心實(shí)例),這些注冊(cè)中心實(shí)例之間并無數(shù)據(jù)交互,數(shù)據(jù)統(tǒng)一存在后端的數(shù)據(jù)源里,實(shí)現(xiàn)數(shù)據(jù)最終一致。


圖7:注冊(cè)中心統(tǒng)一數(shù)據(jù)源

還有一種方案的變種是放在一個(gè)文件系統(tǒng)里,自己做數(shù)據(jù)同步,如圖 8 所示。

圖8:注冊(cè)中心數(shù)據(jù)源數(shù)據(jù)同步

Eureka 的設(shè)計(jì)就是圖 8 的簡化版本,它把 Data replicate 和 Registry Proxy 都放在 Eureka-Server 里。

** 階段二:注冊(cè)中心提高性能 **
只有數(shù)據(jù)源扛得住,注冊(cè)中心實(shí)例其實(shí)是可以無限擴(kuò)展的。
這種代理模式的注冊(cè)中心還有個(gè)好處就是:代理的業(yè)務(wù)邏輯可以自己編寫。這個(gè)地方可以優(yōu)化的地方非常的多。
例如服務(wù)節(jié)點(diǎn)推送,在CP系統(tǒng)里基本上都是推送全量的服務(wù)節(jié)點(diǎn),而在代理里面可以做推送變化部分的服務(wù)節(jié)點(diǎn)。假如一個(gè)服務(wù)有1000個(gè)服務(wù)提供者,5000個(gè)服務(wù)調(diào)用者;當(dāng)增加了1個(gè)服務(wù)提供者的時(shí)候,原來的推送數(shù)量是1001x5000,而代理模式可以進(jìn)行特殊處理變成1x5000,大大減少推送數(shù)據(jù)。

** 階段三:服務(wù)高可用 **
同 CP 注冊(cè)中心高可用。

** 階段四:跨機(jī)房容災(zāi) **
大部分依賴數(shù)據(jù)源的跨機(jī)房容災(zāi)。當(dāng)然可以做一些緩存,例如本地緩存等等。
以數(shù)據(jù)庫為例。

圖9:注冊(cè)中心只讀緩存

注冊(cè)中心的只讀緩存,如果內(nèi)存里放得下則可以放在注冊(cè)中心實(shí)例的內(nèi)存里,如果放不下則可以是單獨(dú)的存儲(chǔ)服務(wù)。
當(dāng)主庫機(jī)房掛了,其它機(jī)房切到新的主庫。 切換期間只能從注冊(cè)中心只讀緩存里讀數(shù)據(jù),但是不能修改數(shù)據(jù)。

如果是基于文件系統(tǒng)的,那么只有保證網(wǎng)絡(luò)分區(qū)的時(shí)候,保證可以臟讀即可。

** 階段5:跨機(jī)房數(shù)據(jù)訪問 **
和 CP 類注冊(cè)中心類似,可能在多個(gè)機(jī)房都會(huì)部署獨(dú)立的注冊(cè)中心,而且服務(wù)數(shù)據(jù)是全局共享的。
一種方案就是多個(gè)注冊(cè)中心直接做數(shù)據(jù)同步、聚合,圖9 中的 DB 主從可以換成其它數(shù)據(jù)源。

圖9:注冊(cè)中心數(shù)據(jù)源數(shù)據(jù)同步

另外一種是注冊(cè)中心實(shí)例對(duì)數(shù)據(jù)源的數(shù)據(jù)多寫,圖10 中的 DB 主從可以換成其它數(shù)據(jù)源。這樣做的話,每個(gè)數(shù)據(jù)源里的數(shù)據(jù)是最終一致的。

圖10:注冊(cè)中心實(shí)例數(shù)據(jù)源多寫

** 階段6:數(shù)據(jù)無限水平擴(kuò)展 **
當(dāng)數(shù)據(jù)量大到單機(jī)無法承受,那么就需要進(jìn)行數(shù)據(jù)分片了。
有了注冊(cè)中心實(shí)例(Proxy)的存在,這個(gè)事情就很好處理了,只需要在這個(gè)注冊(cè)中心實(shí)例上增加分片的邏輯,原則上數(shù)據(jù)是可以無限擴(kuò)展的,而且也不用修改客戶端的邏輯,實(shí)現(xiàn)真正的輕客戶端。

6. 結(jié)束語

最后還是那句話,架構(gòu)是演進(jìn)來的,目前絕大部分使用者還屬于小型注冊(cè)中心階段,真正需要考慮跨機(jī)房容災(zāi)的其實(shí)不多,不需要在一開始就考慮最終級(jí)的架構(gòu)方案。經(jīng)常聽見有的初級(jí)使用者就說 Zookeeper 這不好那不行有很多坑,很多時(shí)候都是場景沒用好或者考慮不夠,如果目前就百來個(gè)接口千來個(gè)客戶端的服務(wù)注冊(cè)中心,就沒啥好糾結(jié)的了,隨便哪個(gè)方案都能Hold住你的需求。

本文如有理解錯(cuò)誤之處,還請(qǐng)指出,十分感謝。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容