国产 无码 综合区,色欲AV无码国产永久播放,无码天堂亚洲国产AV,国产日韩欧美女同一区二区

Zookeeper六大應(yīng)用場(chǎng)景詳解

這篇具有很好參考價(jià)值的文章主要介紹了Zookeeper六大應(yīng)用場(chǎng)景詳解。希望對(duì)大家有所幫助。如果存在錯(cuò)誤或未考慮完全的地方,請(qǐng)大家不吝賜教,您也可以點(diǎn)擊"舉報(bào)違法"按鈕提交疑問(wèn)。

ZooKeeper是?個(gè)典型的發(fā)布/訂閱模式的分布式數(shù)據(jù)管理與協(xié)調(diào)框架,我們可以使用它來(lái)進(jìn)行分布式數(shù)據(jù)的發(fā)布與訂閱。另?方面,通過(guò)對(duì)ZooKeeper中豐富的數(shù)據(jù)節(jié)點(diǎn)類型進(jìn)行交叉使用,配合Watcher 事件通知機(jī)制,可以非常方便地構(gòu)建?系列分布式應(yīng)用中都會(huì)涉及的核心功能,如數(shù)據(jù)發(fā)布/訂閱、命名服務(wù)、集群管理、Master選舉、分布式鎖和分布式隊(duì)列等。那接下來(lái)就針對(duì)這些典型的分布式應(yīng)用場(chǎng)景來(lái)做下介紹。

1. 數(shù)據(jù)發(fā)布/訂閱

數(shù)據(jù)發(fā)布/訂閱(Publish/Subscribe)系統(tǒng),即所謂的配置中心,顧名思義就是發(fā)布者將數(shù)據(jù)發(fā)布到 ZooKeeper的?個(gè)或?系列節(jié)點(diǎn)上,供訂閱者進(jìn)行數(shù)據(jù)訂閱,進(jìn)而達(dá)到動(dòng)態(tài)獲取數(shù)據(jù)的?的,實(shí)現(xiàn)配置信息的集中式管理和數(shù)據(jù)的動(dòng)態(tài)更新。

發(fā)布/訂閱系統(tǒng)?般有兩種設(shè)計(jì)模式,分別是**推(Push)模式和拉(Pull)**模式。在推模式中,服務(wù)端 主動(dòng)將數(shù)據(jù)更新發(fā)送給所有訂閱的客戶端;而拉模式則是由客戶端主動(dòng)發(fā)起請(qǐng)求來(lái)獲取最新數(shù)據(jù),通常 客戶端都采用定時(shí)進(jìn)行輪詢拉取的方式。

如果將配置信息存放到ZooKeeper上進(jìn)行集中管理,那么通常情況下,應(yīng)用在啟動(dòng)的時(shí)候都會(huì)主動(dòng)到 ZooKeeper服務(wù)端上進(jìn)行?次配置信息的獲取,同時(shí),在指定節(jié)點(diǎn)上注冊(cè)?個(gè)Watcher監(jiān)聽(tīng),這樣?來(lái),但凡配置信息發(fā)?變更,服務(wù)端都會(huì)實(shí)時(shí)通知到所有訂閱的客戶端,從而達(dá)到實(shí)時(shí)獲取最新配置信 息的?的。

下面我們通過(guò)?個(gè)“配置管理”的實(shí)際案例來(lái)展示ZooKeeper在“數(shù)據(jù)發(fā)布/訂閱”場(chǎng)景下的使用方式。

在我們平常的應(yīng)用系統(tǒng)開(kāi)發(fā)中,經(jīng)常會(huì)碰到這樣的需求:系統(tǒng)中需要使用?些通用的配置信息,例如機(jī) 器列表信息、運(yùn)行時(shí)的開(kāi)關(guān)配置、數(shù)據(jù)庫(kù)配置信息等。這些全局配置信息通常具備以下3個(gè)特性。

  • 數(shù)據(jù)量通常比較小。
  • 數(shù)據(jù)內(nèi)容在運(yùn)行時(shí)會(huì)發(fā)?動(dòng)態(tài)變化。
  • 集群中各機(jī)器共享,配置?致。

對(duì)于這類配置信息,?般的做法通??梢赃x擇將其存儲(chǔ)在本地配置?件或是內(nèi)存變量中。無(wú)論采用哪種方式,其實(shí)都可以簡(jiǎn)單地實(shí)現(xiàn)配置管理,在集群機(jī)器規(guī)模不大、配置變更不是特別頻繁的情況下,無(wú)論剛剛提到的哪種方式,都能夠非常方便地解決配置管理的問(wèn)題。但是,?旦機(jī)器規(guī)模變大,且配置信息 變更越來(lái)越頻繁后,我們發(fā)現(xiàn)依靠現(xiàn)有的這兩種方式解決配置管理就變得越來(lái)越困難了。我們既希望能夠快速地做到全局配置信息的變更,同時(shí)希望變更成本足夠小,因此我們必須尋求?種更為分布式化的 解決方案接下來(lái)我們就以?個(gè)“數(shù)據(jù)庫(kù)切換”的應(yīng)用場(chǎng)景展開(kāi),看看如何使用ZooKeeper來(lái)實(shí)現(xiàn)配置管理:

  • 配置存儲(chǔ)

在進(jìn)行配置管理之前,?先我們需要將初始化配置信息存儲(chǔ)到Zookeeper上去,?般情況下,我們可以在Zookeeper上選取?個(gè)數(shù)據(jù)節(jié)點(diǎn)用于配置信息的存儲(chǔ),例如:/app1/database_config

zookeeper主流應(yīng)用場(chǎng)景有哪些,Zookeeper,java-zookeeper,zookeeper,分布式

配置管理的zookeeper節(jié)點(diǎn)示意圖 我們將需要管理的配置信息寫入到該數(shù)據(jù)節(jié)點(diǎn)中去,例如:

#數(shù)據(jù)庫(kù)配置信息
#DBCP
dbcp.driverClassName=com.mysql.jdbc.Driver
dbcp.dbJDBCUrl=jdbc:mysql://127.0.0.1:3306/lagou-test
dbcp.username=zm
dbcp.password=1234
dbcp.maxActive=30
dbcp.maxIdle=10

配置獲取

集群中每臺(tái)機(jī)器在啟動(dòng)初始化階段,?先會(huì)從上面提到的ZooKeeper配置節(jié)點(diǎn)上讀取數(shù)據(jù)庫(kù)信息,同時(shí),客戶端還需要在該配置節(jié)點(diǎn)上注冊(cè)?個(gè)數(shù)據(jù)變更的 Watcher監(jiān)聽(tīng),?旦發(fā)?節(jié)點(diǎn)數(shù)據(jù)變更,所有訂閱的客戶端都能夠獲取到數(shù)據(jù)變更通知。

配置變更

在系統(tǒng)運(yùn)行過(guò)程中,可能會(huì)出現(xiàn)需要進(jìn)行數(shù)據(jù)庫(kù)切換的情況,這個(gè)時(shí)候就需要進(jìn)行配置變更。借助 ZooKeeper,我們只需要對(duì)ZooKeeper上配置節(jié)點(diǎn)的內(nèi)容進(jìn)行更新,ZooKeeper就能夠幫我們將數(shù)據(jù)變更的通知發(fā)送到各個(gè)客戶端,每個(gè)客戶端在接收到這個(gè)變更通知后,就可以重新進(jìn)行最新數(shù)據(jù)的獲取。

2. 命名服務(wù)

命名服務(wù)(Name Service)也是分布式系統(tǒng)中比較常見(jiàn)的?類場(chǎng)景,是分布式系統(tǒng)最基本的公共服務(wù)之 ?。在分布式系統(tǒng)中,被命名的實(shí)體通??梢允羌褐械臋C(jī)器、提供的服務(wù)地址或遠(yuǎn)程對(duì)象等——這些我們都可以統(tǒng)稱它們?yōu)槊郑∟ame),其中較為常見(jiàn)的就是?些分布式服務(wù)框架(如RPC、RMI)中的服務(wù)地址列表,通過(guò)使用命名服務(wù),客戶端應(yīng)用能夠根據(jù)指定名字來(lái)獲取資源的實(shí)體、服務(wù)地址和提供者的信息等。

ZooKeeper 提供的命名服務(wù)功能能夠幫助應(yīng)用系統(tǒng)通過(guò)?個(gè)資源引用的方式來(lái)實(shí)現(xiàn)對(duì)資源的定位與使用。另外,廣義上命名服務(wù)的資源定位都不是真正意義的實(shí)體資源——在分布式環(huán)境中,上層應(yīng)用僅僅需要?個(gè)全局唯?的名字,類似于數(shù)據(jù)庫(kù)中的唯?主鍵。

所以接下來(lái)。我們來(lái)看看如何使用ZooKeeper來(lái)實(shí)現(xiàn)?套分布式全局唯?ID的分配機(jī)制

所謂ID,就是?個(gè)能夠唯?標(biāo)識(shí)某個(gè)對(duì)象的標(biāo)識(shí)符。在我們熟悉的關(guān)系型數(shù)據(jù)庫(kù)中,各個(gè)表都需要?個(gè)主鍵來(lái)唯?標(biāo)識(shí)每條數(shù)據(jù)庫(kù)記錄,這個(gè)主鍵就是這樣的唯?ID。在過(guò)去的單庫(kù)單表型系統(tǒng)中,通常可以使用數(shù)據(jù)庫(kù)字段自帶的auto_increment屬性來(lái)自動(dòng)為每條數(shù)據(jù)庫(kù)記錄?成?個(gè)唯?的ID,數(shù)據(jù)庫(kù)會(huì)保證?成的這個(gè)ID在全局唯?。但是隨著數(shù)據(jù)庫(kù)數(shù)據(jù)規(guī)模的不斷增大,分庫(kù)分表隨之出現(xiàn),而 auto_increment屬性僅能針對(duì)單?表中的記錄自動(dòng)?成ID,因此在這種情況下,就無(wú)法再依靠數(shù)據(jù)庫(kù)的 auto_increment屬性來(lái)唯?標(biāo)識(shí)?條記錄了。于是,我們必須尋求?種能夠在分布式環(huán)境下?成全局唯?ID的方法。

?說(shuō)起全局唯? ID,相信大家都會(huì)聯(lián)想到 UUID。沒(méi)錯(cuò),UUID 是通用唯?識(shí)別碼(Universally Unique Identifier)的簡(jiǎn)稱,是?種在分布式系統(tǒng)中廣泛使用的用于唯?標(biāo)識(shí)元素的標(biāo)準(zhǔn) 確實(shí),UUID 是?個(gè)非常不錯(cuò)的全局唯?ID?成方式,能夠非常簡(jiǎn)便地保證分布式環(huán)境中的唯?性。?個(gè)標(biāo)準(zhǔn)的 UUID 是?個(gè)包含 32 位字符和 4 個(gè)短線的字符串,例如e70f1357-f260-46ff-a32d-53a086c57ade。 UUID的優(yōu)勢(shì)自然不必多說(shuō),我們重點(diǎn)來(lái)看看它的缺陷。

長(zhǎng)度過(guò)長(zhǎng)

UUID 最大的問(wèn)題就在于?成的字符串過(guò)長(zhǎng)。顯然,和數(shù)據(jù)庫(kù)中的 INT 類型相比,存儲(chǔ)?個(gè)UUID需要花 費(fèi)更多的空間。

含義不明

上面我們已經(jīng)看到?個(gè)典型的 UUID 是類似于“e70f1357-f260-46ff-a32d-53a086c57ade”的?個(gè)字符 串。根據(jù)這個(gè)字符串,開(kāi)發(fā)人員從字面上基本看不出任何其表達(dá)的含義,這將會(huì)大大影響問(wèn)題排查和開(kāi) 發(fā)調(diào)試的效率。

所以接下來(lái),我們結(jié)合?個(gè)分布式任務(wù)調(diào)度系統(tǒng)來(lái)看看如何使用ZooKeepe來(lái)實(shí)現(xiàn)這類全局唯?ID的? 成。 之前我們已經(jīng)提到,通過(guò)調(diào)用ZooKeeper節(jié)點(diǎn)創(chuàng)建的API接?可以創(chuàng)建?個(gè)順序節(jié)點(diǎn),并且在API返 回值中會(huì)返回這個(gè)節(jié)點(diǎn)的完整名字。利用這個(gè)特性,我們就可以借助ZooKeeper來(lái)?成全局唯?的ID了,如下圖:

zookeeper主流應(yīng)用場(chǎng)景有哪些,Zookeeper,java-zookeeper,zookeeper,分布式

全局唯?ID?成的ZooKeeper節(jié)點(diǎn)示意圖

說(shuō)明,對(duì)于?個(gè)任務(wù)列表的主鍵,使用ZooKeeper?成唯?ID的基本步驟:

  • 所有客戶端都會(huì)根據(jù)自己的任務(wù)類型,在指定類型的任務(wù)下面通過(guò)調(diào)用create()接?來(lái)創(chuàng)建?個(gè)順序節(jié)點(diǎn),例如創(chuàng)建“job-”節(jié)點(diǎn)。
  • 節(jié)點(diǎn)創(chuàng)建完畢后,create()接?會(huì)返回?個(gè)完整的節(jié)點(diǎn)名,例如“job-0000000003”。
  • 客戶端拿到這個(gè)返回值后,拼接上 type 類型,例如“type2-job-0000000003”,這就可以作為?個(gè) 全局唯?的ID了。

在ZooKeeper中,每?個(gè)數(shù)據(jù)節(jié)點(diǎn)都能夠維護(hù)?份子節(jié)點(diǎn)的順序順列,當(dāng)客戶端對(duì)其創(chuàng)建?個(gè)順序子節(jié) 點(diǎn)的時(shí)候 ZooKeeper 會(huì)自動(dòng)以后綴的形式在其子節(jié)點(diǎn)上添加?個(gè)序號(hào),在這個(gè)場(chǎng)景中就是利用了 ZooKeeper的這個(gè)特性

3. 集群管理

隨著分布式系統(tǒng)規(guī)模的日益擴(kuò)大,集群中的機(jī)器規(guī)模也隨之變大,那如何更好地進(jìn)行集群管理也顯得越來(lái)越重要了。所謂集群管理,包括集群監(jiān)控與集群控制兩大塊,前者側(cè)重對(duì)集群運(yùn)行時(shí)狀態(tài)的收集,后者則是對(duì)集群進(jìn)行操作與控制。

在日常開(kāi)發(fā)和運(yùn)維過(guò)程中,我們經(jīng)常會(huì)有類似于如下的需求:

  • 如何快速的統(tǒng)計(jì)出當(dāng)前?產(chǎn)環(huán)境下?共有多少臺(tái)機(jī)器
  • 如何快速的獲取到機(jī)器上下線的情況
  • 如何實(shí)時(shí)監(jiān)控集群中每臺(tái)主機(jī)的運(yùn)行時(shí)狀態(tài)

在傳統(tǒng)的基于Agent的分布式集群管理體系中,都是通過(guò)在集群中的每臺(tái)機(jī)器上部署?個(gè)Agent,由這 個(gè) Agent 負(fù)責(zé)主動(dòng)向指定的?個(gè)監(jiān)控中心系統(tǒng)(監(jiān)控中心系統(tǒng)負(fù)責(zé)將所有數(shù)據(jù)進(jìn)行集中處理,形成?系列報(bào)表,并負(fù)責(zé)實(shí)時(shí)報(bào)警,以下簡(jiǎn)稱“監(jiān)控中心”)匯報(bào)自己所在機(jī)器的狀態(tài)。在集群規(guī)模適中的場(chǎng)景 下,這確實(shí)是?種在?產(chǎn)實(shí)踐中廣泛使用的解決方案,能夠快速有效地實(shí)現(xiàn)分布式環(huán)境集群監(jiān)控,但是?旦系統(tǒng)的業(yè)務(wù)場(chǎng)景增多,集群規(guī)模變大之后,該解決方案的弊端也就顯現(xiàn)出來(lái)了。

大規(guī)模升級(jí)困難

以客戶端形式存在的 Agent,在大規(guī)模使用后,?旦遇上需要大規(guī)模升級(jí)的情況,就非常麻煩,在升級(jí)成本和升級(jí)進(jìn)度的控制上面臨巨大的挑戰(zhàn)。

統(tǒng)?的Agent無(wú)法滿足多樣的需求

對(duì)于機(jī)器的CPU使用率、負(fù)載(Load)、內(nèi)存使用率、網(wǎng)絡(luò)吞吐以及磁盤容量等機(jī)器基本的物理狀態(tài), 使用統(tǒng)?的Agent來(lái)進(jìn)行監(jiān)控或許都可以滿足。但是,如果需要深入應(yīng)用內(nèi)部,對(duì)?些業(yè)務(wù)狀態(tài)進(jìn)行監(jiān)控,例如,在?個(gè)分布式消息中間件中,希望監(jiān)控到每個(gè)消費(fèi)者對(duì)消息的消費(fèi)狀態(tài);或者在?個(gè)分布式任務(wù)調(diào)度系統(tǒng)中,需要對(duì)每個(gè)機(jī)器上任務(wù)的執(zhí)行情況進(jìn)行監(jiān)控。很顯然,對(duì)于這些業(yè)務(wù)耦合緊密的監(jiān)控需求,不適合由?個(gè)統(tǒng)?的Agent來(lái)提供。

編程語(yǔ)?多樣性

隨著越來(lái)越多編程語(yǔ)?的出現(xiàn),各種異構(gòu)系統(tǒng)層出不窮。如果使用傳統(tǒng)的Agent方式,那么需要提供各種語(yǔ)?的 Agent 客戶端。另?方面,“監(jiān)控中心”在對(duì)異構(gòu)系統(tǒng)的數(shù)據(jù)進(jìn)行整合上面臨巨大挑戰(zhàn)。

Zookeeper的兩大特性:

  1. 客戶端如果對(duì)Zookeeper的數(shù)據(jù)節(jié)點(diǎn)注冊(cè)Watcher監(jiān)聽(tīng),那么當(dāng)該數(shù)據(jù)節(jié)點(diǎn)的內(nèi)容或是其子節(jié)點(diǎn)列表發(fā)?變更時(shí),Zookeeper服務(wù)器就會(huì)向訂閱的客戶端發(fā)送變更通知。
  2. 對(duì)在Zookeeper上創(chuàng)建的臨時(shí)節(jié)點(diǎn),?旦客戶端與服務(wù)器之間的會(huì)話失效,那么臨時(shí)節(jié)點(diǎn)也會(huì)被自動(dòng)刪除利用其兩大特性,可以實(shí)現(xiàn)集群機(jī)器存活監(jiān)控系統(tǒng),若監(jiān)控系統(tǒng)在/clusterServers節(jié)點(diǎn)上注冊(cè)?個(gè) Watcher監(jiān)聽(tīng),那么但凡進(jìn)行動(dòng)態(tài)添加機(jī)器的操作,就會(huì)在/clusterServers節(jié)點(diǎn)下創(chuàng)建?個(gè)臨時(shí)節(jié) 點(diǎn):/clusterServers/[Hostname],這樣,監(jiān)控系統(tǒng)就能夠?qū)崟r(shí)監(jiān)測(cè)機(jī)器的變動(dòng)情況。 下面通過(guò)分布式日志收集系統(tǒng)這個(gè)典型應(yīng)用來(lái)學(xué)習(xí)Zookeeper如何實(shí)現(xiàn)集群管理。

分布式日志收集系統(tǒng)

分布式日志收集系統(tǒng)的核心工作就是收集分布在不同機(jī)器上的系統(tǒng)日志,在這?我們重點(diǎn)來(lái)看分布式日志系統(tǒng)(以下簡(jiǎn)稱“日志系統(tǒng)”)的收集器模塊。 在?個(gè)典型的日志系統(tǒng)的架構(gòu)設(shè)計(jì)中,整個(gè)日志系統(tǒng)會(huì)把所有需要收集的日志機(jī)器(我們以“日志源機(jī) 器”代表此類機(jī)器)分為多個(gè)組別,每個(gè)組別對(duì)應(yīng)?個(gè)收集器,這個(gè)收集器其實(shí)就是?個(gè)后臺(tái)機(jī)器(我們 以“收集器機(jī)器”代表此類機(jī)器),用于收集日志對(duì)于大規(guī)模的分布式日志收集系統(tǒng)場(chǎng)景,通常需要解決兩個(gè)問(wèn)題:

  • 變化的日志源機(jī)器

    在?產(chǎn)環(huán)境中,伴隨著機(jī)器的變動(dòng),每個(gè)應(yīng)用的機(jī)器?乎每天都是在變化的(機(jī)器硬件問(wèn)題、擴(kuò)容、機(jī)房 遷移或是網(wǎng)絡(luò)問(wèn)題等都會(huì)導(dǎo)致?個(gè)應(yīng)用的機(jī)器變化),也就是說(shuō)每個(gè)組別中的日志源機(jī)器通常是在不斷變化的

  • 變化的收集器機(jī)器

    日志收集系統(tǒng)自身也會(huì)有機(jī)器的變更或擴(kuò)容,于是會(huì)出現(xiàn)新的收集器機(jī)器加入或是?的收集器機(jī)器退出的情況。

無(wú)論是日志源機(jī)器還是收集器機(jī)器的變更,最終都可以歸結(jié)為如何快速、合理、動(dòng)態(tài)地為每個(gè)收集器分配對(duì)應(yīng)的日志源機(jī)器。這也成為了整個(gè)日志系統(tǒng)正確穩(wěn)定運(yùn)轉(zhuǎn)的前提,也是日志收集過(guò)程中最大的技術(shù)挑戰(zhàn)之?,在這種情況下,我們就可以引入zookeeper了,下面我們就來(lái)看ZooKeeper在這個(gè)場(chǎng)景中的使用。

使用Zookeeper的場(chǎng)景步驟如下

  1. 注冊(cè)收集器機(jī)器

使用ZooKeeper來(lái)進(jìn)行日志系統(tǒng)收集器的注冊(cè),典型做法是在ZooKeeper上創(chuàng)建?個(gè)節(jié)點(diǎn)作為收集器的根節(jié)點(diǎn),例如/logs/collector(下?我們以“收集器節(jié)點(diǎn)”代表該數(shù)據(jù)節(jié)點(diǎn)),每個(gè)收集器機(jī)器在啟動(dòng)的時(shí)候,都會(huì)在收集器節(jié)點(diǎn)下創(chuàng)建自己的節(jié)點(diǎn),例如/logs/collector/[Hostname]

zookeeper主流應(yīng)用場(chǎng)景有哪些,Zookeeper,java-zookeeper,zookeeper,分布式

  1. 任務(wù)分發(fā)

    待所有收集器機(jī)器都創(chuàng)建好自己對(duì)應(yīng)的節(jié)點(diǎn)后,系統(tǒng)根據(jù)收集器節(jié)點(diǎn)下子節(jié)點(diǎn)的個(gè)數(shù),將所有日志源機(jī)器分成對(duì)應(yīng)的若干組,然后將分組后的機(jī)器列表分別寫到這些收集器機(jī)器創(chuàng)建的子節(jié)點(diǎn)(例 如/logs/collector/host1)上去。這樣?來(lái),每個(gè)收集器機(jī)器都能夠從自己對(duì)應(yīng)的收集器節(jié)點(diǎn)上獲取日志源機(jī)器列表,進(jìn)而開(kāi)始進(jìn)行日志收集工作。

  2. 狀態(tài)匯報(bào)

    完成收集器機(jī)器的注冊(cè)以及任務(wù)分發(fā)后,我們還要考慮到這些機(jī)器隨時(shí)都有掛掉的可能。因此,針對(duì)這個(gè)問(wèn)題,我們需要有?個(gè)收集器的狀態(tài)匯報(bào)機(jī)制:每個(gè)收集器機(jī)器在創(chuàng)建完自己的專屬節(jié)點(diǎn)后,還需要在對(duì)應(yīng)的子節(jié)點(diǎn)上創(chuàng)建?個(gè)狀態(tài)子節(jié)點(diǎn),例如/logs/collector/host1/status,每個(gè)收集器機(jī)器都需要定期向該節(jié)點(diǎn)寫入自己的狀態(tài)信息。我們可以把這種策略看作是?種心跳檢測(cè)機(jī)制,通常收集器機(jī)器都會(huì)在這個(gè)節(jié)點(diǎn)中寫入日志收集進(jìn)度信息。日志系統(tǒng)根據(jù)該狀態(tài)子節(jié)點(diǎn)的最后更新時(shí)間來(lái)判斷對(duì)應(yīng)的收集器機(jī)器是否存活。

  3. 動(dòng)態(tài)分配

    如果收集器機(jī)器掛掉或是擴(kuò)容了,就需要?jiǎng)討B(tài)地進(jìn)行收集任務(wù)的分配。在運(yùn)行過(guò)程中,日志系統(tǒng)始終關(guān)注著/logs/collector這個(gè)節(jié)點(diǎn)下所有子節(jié)點(diǎn)的變更,?旦檢測(cè)到有收集器機(jī)器停?匯報(bào)或是有新的收集器機(jī)器加入,就要開(kāi)始進(jìn)行任務(wù)的重新分配。無(wú)論是針對(duì)收集器機(jī)器停?匯報(bào)還是新機(jī)器加入的情況, 日志系統(tǒng)都需要將之前分配給該收集器的所有任務(wù)進(jìn)行轉(zhuǎn)移。為了解決這個(gè)問(wèn)題,通常有兩種做法:

    • 全局動(dòng)態(tài)分配

      這是?種簡(jiǎn)單粗暴的做法,在出現(xiàn)收集器機(jī)器掛掉或是新機(jī)器加入的時(shí)候,日志系統(tǒng)需要根據(jù)新的收集器機(jī)器列表,立即對(duì)所有的日志源機(jī)器重新進(jìn)行?次分組,然后將其分配給剩下的收集器機(jī)器。

    • 局部動(dòng)態(tài)分配

      全局動(dòng)態(tài)分配方式雖然策略簡(jiǎn)單,但是存在?個(gè)問(wèn)題:?個(gè)或部分收集器機(jī)器的變更,就會(huì)導(dǎo)致全局動(dòng)態(tài)任務(wù)的分配,影響面比較大,因此?險(xiǎn)也就比較大。所謂局部動(dòng)態(tài)分配,顧名思義就是在小范圍內(nèi)進(jìn) 行任務(wù)的動(dòng)態(tài)分配。在這種策略中,每個(gè)收集器機(jī)器在匯報(bào)自己日志收集狀態(tài)的同時(shí),也會(huì)把自己的負(fù)載匯報(bào)上去。請(qǐng)注意,這?提到的負(fù)載并不僅僅只是簡(jiǎn)單地指機(jī)器CPU負(fù)載(Load),而是?個(gè)對(duì)當(dāng)前收集器任務(wù)執(zhí)行的綜合評(píng)估,這個(gè)評(píng)估算法和ZooKeeper本身并沒(méi)有太大的關(guān)系,這?不再贅述。 在這種策略中,如果?個(gè)收集器機(jī)器掛了,那么日志系統(tǒng)就會(huì)把之前分配給這個(gè)機(jī)器的任務(wù)重新分配到 那些負(fù)載較低的機(jī)器上去。同樣,如果有新的收集器機(jī)器加入,會(huì)從那些負(fù)載?的機(jī)器上轉(zhuǎn)移部分任務(wù) 給這個(gè)新加入的機(jī)器。

      上述步驟已經(jīng)完整的說(shuō)明了整個(gè)日志收集系統(tǒng)的?作流程,其中有兩點(diǎn)注意事項(xiàng):

    ① 節(jié)點(diǎn)類型

    在/logs/collector節(jié)點(diǎn)下創(chuàng)建臨時(shí)節(jié)點(diǎn)可以很好的判斷機(jī)器是否存活,但是,若機(jī)器掛了,其節(jié)點(diǎn)會(huì)被 刪除,記錄在節(jié)點(diǎn)上的日志源機(jī)器列表也被清除,所以需要選擇持久節(jié)點(diǎn)來(lái)標(biāo)識(shí)每?臺(tái)機(jī)器,同時(shí)在節(jié) 點(diǎn)下分別創(chuàng)建/logs/collector/[Hostname]/status節(jié)點(diǎn)來(lái)表征每?個(gè)收集器機(jī)器的狀態(tài),這樣,既能實(shí) 現(xiàn)對(duì)所有機(jī)器的監(jiān)控,同時(shí)機(jī)器掛掉后,依然能夠?qū)⒎峙淙蝿?wù)還原。

    ② 日志系統(tǒng)節(jié)點(diǎn)監(jiān)聽(tīng)

    若采用Watcher機(jī)制,那么通知的消息量的網(wǎng)絡(luò)開(kāi)銷非常大,需要采用日志系統(tǒng)主動(dòng)輪詢收集器節(jié)點(diǎn)的 策略,這樣可以節(jié)省網(wǎng)絡(luò)流量,但是存在?定的延時(shí)。

4. Master選舉

Master選舉是?個(gè)在分布式系統(tǒng)中非常常見(jiàn)的應(yīng)用場(chǎng)景。分布式最核心的特性就是能夠?qū)⒕哂歇?dú)立計(jì)算能力的系統(tǒng)單元部署在不同的機(jī)器上,構(gòu)成?個(gè)完整的分布式系統(tǒng)。而與此同時(shí),實(shí)際場(chǎng)景中往往也需要在這些分布在不同機(jī)器上的獨(dú)立系統(tǒng)單元中選出?個(gè)所謂的“?大”,在計(jì)算機(jī)中,我們稱之為 Master。

在分布式系統(tǒng)中,Master往往用來(lái)協(xié)調(diào)集群中其他系統(tǒng)單元,具有對(duì)分布式系統(tǒng)狀態(tài)變更的決定權(quán)。例如,在?些讀寫分離的應(yīng)用場(chǎng)景中,客戶端的寫請(qǐng)求往往是由 Master來(lái)處理的;而在另?些場(chǎng)景中, Master則常常負(fù)責(zé)處理?些復(fù)雜的邏輯,并將處理結(jié)果同步給集群中其他系統(tǒng)單元。Master選舉可以說(shuō)是ZooKeeper最典型的應(yīng)用場(chǎng)景了,接下來(lái),我們就結(jié)合“?種海量數(shù)據(jù)處理與共享模型”這個(gè)具體例子來(lái)看看 ZooKeeper在集群Master選舉中的應(yīng)用場(chǎng)景。

在分布式環(huán)境中,經(jīng)常會(huì)碰到這樣的應(yīng)用場(chǎng)景:集群中的所有系統(tǒng)單元需要對(duì)前端業(yè)務(wù)提供數(shù)據(jù),比如 ?個(gè)商品 ID,或者是?個(gè)網(wǎng)站輪播廣告的廣告 ID(通常出現(xiàn)在?些廣告投放系統(tǒng)中)等,而這些商品 ID或是廣告ID往往需要從?系列的海量數(shù)據(jù)處理中計(jì)算得到——這通常是?個(gè)非常耗費(fèi) I/O 和 CPU資源 的過(guò)程。鑒于該計(jì)算過(guò)程的復(fù)雜性,如果讓集群中的所有機(jī)器都執(zhí)行這個(gè)計(jì)算邏輯的話,那么將耗費(fèi)非常多的資源。?種比較好的方法就是只讓集群中的部分,甚?只讓其中的?臺(tái)機(jī)器去處理數(shù)據(jù)計(jì)算,? 旦計(jì)算出數(shù)據(jù)結(jié)果,就可以共享給整個(gè)集群中的其他所有客戶端機(jī)器,這樣可以大大減少重復(fù)勞動(dòng),提 升性能。 這?我們以?個(gè)簡(jiǎn)單的廣告投放系統(tǒng)后臺(tái)場(chǎng)景為例來(lái)講解這個(gè)模型。

zookeeper主流應(yīng)用場(chǎng)景有哪些,Zookeeper,java-zookeeper,zookeeper,分布式

整個(gè)系統(tǒng)大體上可以分成客戶端集群、分布式緩存系統(tǒng)、海量數(shù)據(jù)處理總線和 ZooKeeper四個(gè)部分

?先我們來(lái)看整個(gè)系統(tǒng)的運(yùn)行機(jī)制。圖中的Client集群每天定時(shí)會(huì)通過(guò)ZooKeeper來(lái)實(shí)現(xiàn)Master選舉。 選舉產(chǎn)?Master客戶端之后,這個(gè)Master就會(huì)負(fù)責(zé)進(jìn)行?系列的海量數(shù)據(jù)處理,最終計(jì)算得到?個(gè)數(shù)據(jù)結(jié)果,并將其放置在?個(gè)內(nèi)存/數(shù)據(jù)庫(kù)中。同時(shí),Master還需要通知集群中其他所有的客戶端從這個(gè)內(nèi)存/數(shù)據(jù)庫(kù)中共享計(jì)算結(jié)果。

接下去,我們將重點(diǎn)來(lái)看 Master 選舉的過(guò)程,?先來(lái)明確下 Master 選舉的需求:在集群的所有機(jī)器中選舉出?臺(tái)機(jī)器作為Master。針對(duì)這個(gè)需求,通常情況下,我們可以選擇常見(jiàn)的關(guān)系型數(shù)據(jù)庫(kù)中的主鍵特性來(lái)實(shí)現(xiàn):集群中的所有機(jī)器都向數(shù)據(jù)庫(kù)中插入?條相同主鍵 ID 的記錄,數(shù)據(jù)庫(kù)會(huì)幫助我們?動(dòng) 進(jìn)行主鍵沖突檢查,也就是說(shuō),所有進(jìn)行插入操作的客戶端機(jī)器中,只有?臺(tái)機(jī)器能夠成功——那么, 我們就認(rèn)為向數(shù)據(jù)庫(kù)中成功插入數(shù)據(jù)的客戶端機(jī)器成為Master。 借助數(shù)據(jù)庫(kù)的這種方案確實(shí)可行,依靠關(guān)系型數(shù)據(jù)庫(kù)的主鍵特性能夠很好地保證在集群中選舉出唯?的 ?個(gè)Master。但是我們需要考慮的另?個(gè)問(wèn)題是,如果當(dāng)前選舉出的Master掛了,那么該如何處理? 誰(shuí)來(lái)告訴我Master掛了呢?顯然,關(guān)系型數(shù)據(jù)庫(kù)沒(méi)法通知我們這個(gè)事件。那么,如果使用ZooKeeper是否可以做到這?點(diǎn)呢? 那在之前,我們介紹了ZooKeeper創(chuàng)建節(jié)點(diǎn)的API接?,其中?個(gè)重要特性便 是:利用ZooKeeper的強(qiáng)?致性,能夠很好保證在分布式?并發(fā)情況下節(jié)點(diǎn)的創(chuàng)建?定能夠保證全局唯?性,即ZooKeeper將會(huì)保證客戶端無(wú)法重復(fù)創(chuàng)建?個(gè)已經(jīng)存在的數(shù)據(jù)節(jié)點(diǎn)。也就是說(shuō),如果同時(shí)有多個(gè)客戶端請(qǐng)求創(chuàng)建同?個(gè)節(jié)點(diǎn),那么最終?定只有?個(gè)客戶端請(qǐng)求能夠創(chuàng)建成功。利用這個(gè)特性,就能很容易地在分布式環(huán)境中進(jìn)行Master選舉了。

zookeeper主流應(yīng)用場(chǎng)景有哪些,Zookeeper,java-zookeeper,zookeeper,分布式

在這個(gè)系統(tǒng)中,?先會(huì)在 ZooKeeper 上創(chuàng)建?個(gè)日期節(jié)點(diǎn),例如“2020-11-11

客戶端集群每天都會(huì)定時(shí)往ZooKeeper 上創(chuàng)建?個(gè)臨時(shí)節(jié)點(diǎn),例如/master_election/2020-11- 11/binding。在這個(gè)過(guò)程中,只有?個(gè)客戶端能夠成功創(chuàng)建這個(gè)節(jié)點(diǎn),那么這個(gè)客戶端所在的機(jī)器就成為了Master。同時(shí),其他沒(méi)有在ZooKeeper上成功創(chuàng)建節(jié)點(diǎn)的客戶端,都會(huì)在節(jié) 點(diǎn)/master_election/2020-11-11 上注冊(cè)?個(gè)子節(jié)點(diǎn)變更的 Watcher,用于監(jiān)控當(dāng)前的 Master 機(jī)器是否存活,?旦發(fā)現(xiàn)當(dāng)前的 Master 掛了,那么其余的客戶端將會(huì)重新進(jìn)行Master選舉。 從上面的講解中,我們可以看到,如果僅僅只是想實(shí)現(xiàn)Master選舉的話,那么其實(shí)只需要有?個(gè)能夠保證數(shù)據(jù)唯?性的組件即可,例如關(guān)系型數(shù)據(jù)庫(kù)的主鍵模型就是非常不錯(cuò)的選擇。但是,如果希望能夠快速地進(jìn)行集群 Master 動(dòng)態(tài)選舉,那么就可以基于 ZooKeeper來(lái)實(shí)現(xiàn)。

5.分布式鎖

分布式鎖是控制分布式系統(tǒng)之間同步訪問(wèn)共享資源的?種方式。如果不同的系統(tǒng)或是同?個(gè)系統(tǒng)的不同主機(jī)之間共享了?個(gè)或?組資源,那么訪問(wèn)這些資源的時(shí)候,往往需要通過(guò)?些互斥?段來(lái)防?彼此之間的干擾,以保證?致性,在這種情況下,就需要使用分布式鎖了。 在平時(shí)的實(shí)際項(xiàng)?開(kāi)發(fā)中,我們往往很少會(huì)去在意分布式鎖,而是依賴于關(guān)系型數(shù)據(jù)庫(kù)固有的排他性來(lái)實(shí)現(xiàn)不同進(jìn)程之間的互斥。這確實(shí)是?種非常簡(jiǎn)便且被?泛使用的分布式鎖實(shí)現(xiàn)方式。然而有?個(gè)不爭(zhēng) 的事實(shí)是,?前絕大多數(shù)大型分布式系統(tǒng)的性能瓶頸都集中在數(shù)據(jù)庫(kù)操作上。因此,如果上層業(yè)務(wù)再給數(shù)據(jù)庫(kù)添加?些額外的鎖,例如行鎖、表鎖甚?是繁重的事務(wù)處理,那么就會(huì)讓數(shù)據(jù)庫(kù)更加不堪重負(fù) 下面我們來(lái)看看使用ZooKeeper如何實(shí)現(xiàn)分布式鎖,這?主要講解排他鎖和共享鎖兩類分布式鎖。

5.1 排他鎖

排他鎖(Exclusive Locks,簡(jiǎn)稱 X 鎖),?稱為寫鎖或獨(dú)占鎖,是?種基本的鎖類型。如果事務(wù) T1對(duì)數(shù)據(jù)對(duì)象 O1加上了排他鎖,那么在整個(gè)加鎖期間,只允許事務(wù) T1對(duì) O1進(jìn)行讀取和更新操作,其他任何事務(wù)都不能再對(duì)這個(gè)數(shù)據(jù)對(duì)象進(jìn)行任何類型的操作——直到T1釋放了排他鎖

從上面講解的排他鎖的基本概念中,我們可以看到,排他鎖的核心是如何保證當(dāng)前有且僅有?個(gè)事務(wù)獲得鎖,并且鎖被釋放后,所有正在等待獲取鎖的事務(wù)都能夠被通知到。 下面我們就來(lái)看看如何借助ZooKeeper實(shí)現(xiàn)排他鎖:

5.1.1 定義鎖

在通常的Java開(kāi)發(fā)編程中,有兩種常?的?式可以用來(lái)定義鎖,分別是synchronized機(jī)制和JDK5提供的 ReentrantLock。然而,在ZooKeeper中,沒(méi)有類似于這樣的API可以直接使用,而是通過(guò) ZooKeeper 上的數(shù)據(jù)節(jié)點(diǎn)來(lái)表示?個(gè)鎖,例如/exclusive_lock/lock節(jié)點(diǎn)就可以被定義為?個(gè)鎖,如圖:

zookeeper主流應(yīng)用場(chǎng)景有哪些,Zookeeper,java-zookeeper,zookeeper,分布式

5.1.2 獲取鎖

在需要獲取排他鎖時(shí),所有的客戶端都會(huì)試圖通過(guò)調(diào)用 create()接?,在/exclusive_lock節(jié)點(diǎn)下創(chuàng)建臨時(shí)子節(jié)點(diǎn)/exclusive_lock/lock。在前面,我們也介紹了,ZooKeeper 會(huì)保證在所有的客戶端中,最終只有?個(gè)客戶端能夠創(chuàng)建成功,那么就可以認(rèn)為該客戶端獲取了鎖。同時(shí),所有沒(méi)有獲取到鎖的客戶端就需要到/exclusive_lock 節(jié)點(diǎn)上注冊(cè)?個(gè)子節(jié)點(diǎn)變更的Watcher監(jiān)聽(tīng),以便實(shí)時(shí)監(jiān)聽(tīng)到lock節(jié)點(diǎn)的變更情況

5.1.3 釋放鎖

在“定義鎖”部分,我們已經(jīng)提到,/exclusive_lock/lock 是?個(gè)臨時(shí)節(jié)點(diǎn),因此在以下兩種情況下,都有可能釋放鎖。 · 當(dāng)前獲取鎖的客戶端機(jī)器發(fā)?宕機(jī),那么ZooKeeper上的這個(gè)臨時(shí)節(jié)點(diǎn)就會(huì)被移除。正常執(zhí)行完業(yè)務(wù)邏輯后,客戶端就會(huì)主動(dòng)將自己創(chuàng)建的臨時(shí)節(jié)點(diǎn)刪除。無(wú)論在什么情況下移除了lock節(jié) 點(diǎn),ZooKeeper都會(huì)通知所有在/exclusive_lock節(jié)點(diǎn)上注冊(cè)了子節(jié)點(diǎn)變更Watcher監(jiān)聽(tīng)的客戶端。這些 客戶端在接收到通知后,再次重新發(fā)起分布式鎖獲取,即重復(fù)“獲取鎖”過(guò)程。整個(gè)排他鎖的獲取和釋放 流程,如下圖:

zookeeper主流應(yīng)用場(chǎng)景有哪些,Zookeeper,java-zookeeper,zookeeper,分布式

5.2 共享鎖

共享鎖(Shared Locks,簡(jiǎn)稱S鎖),?稱為讀鎖,同樣是?種基本的鎖類型。

如果事務(wù)T1對(duì)數(shù)據(jù)對(duì)象O1加上了共享鎖,那么當(dāng)前事務(wù)只能對(duì)O1進(jìn)行讀取操作,其他事務(wù)也只能對(duì)這個(gè)數(shù)據(jù)對(duì)象加共享鎖——直到該數(shù)據(jù)對(duì)象上的所有共享鎖都被釋放。 共享鎖和排他鎖最根本的區(qū)別在于,加上排他鎖后,數(shù)據(jù)對(duì)象只對(duì)?個(gè)事務(wù)可?,而加上共享鎖后,數(shù)據(jù)對(duì)所有事務(wù)都可?。 下面我們就來(lái)看看如何借助ZooKeeper來(lái)實(shí)現(xiàn)共享鎖。

5.2.1 定義鎖

和排他鎖?樣,同樣是通過(guò) ZooKeeper 上的數(shù)據(jù)節(jié)點(diǎn)來(lái)表示?個(gè)鎖,是?個(gè)類似于 “/shared_lock/[Hostname]-請(qǐng)求類型-序號(hào)”的臨時(shí)順序節(jié)點(diǎn),例如/shared_lock/host1-R-0000000001,那么,這個(gè)節(jié)點(diǎn)就代表了?個(gè)共享鎖,如圖所示:

zookeeper主流應(yīng)用場(chǎng)景有哪些,Zookeeper,java-zookeeper,zookeeper,分布式

5.2.1 獲取鎖

在需要獲取共享鎖時(shí),所有客戶端都會(huì)到/shared_lock 這個(gè)節(jié)點(diǎn)下面創(chuàng)建?個(gè)臨時(shí)順序節(jié)點(diǎn),如果當(dāng)前 是讀請(qǐng)求,那么就創(chuàng)建例如/shared_lock/host1-R-0000000001的節(jié)點(diǎn);如果是寫請(qǐng)求,那么就創(chuàng)建例 如/shared_lock/host2-W-0000000002的節(jié)點(diǎn)。

判斷讀寫順序

通過(guò)Zookeeper來(lái)確定分布式讀寫順序,大致分為四步

  1. 創(chuàng)建完節(jié)點(diǎn)后,獲取/shared_lock節(jié)點(diǎn)下所有子節(jié)點(diǎn),并對(duì)該節(jié)點(diǎn)變更注冊(cè)監(jiān)聽(tīng)。
  2. 確定自己的節(jié)點(diǎn)序號(hào)在所有子節(jié)點(diǎn)中的順序。
  3. 對(duì)于讀請(qǐng)求:若沒(méi)有比自己序號(hào)小的子節(jié)點(diǎn)或所有比自己序號(hào)小的子節(jié)點(diǎn)都是讀請(qǐng)求,那么表 明自己已經(jīng)成功獲取到共享鎖,同時(shí)開(kāi)始執(zhí)行讀取邏輯,若有寫請(qǐng)求,則需要等待。對(duì)于寫請(qǐng)求:若自己不 是序號(hào)最小的子節(jié)點(diǎn),那么需要等待。
  4. 接收到Watcher通知后,重復(fù)步驟1

5.2.2 釋放鎖

其釋放鎖的流程與獨(dú)占鎖?致。

5.3 羊群效應(yīng)

上面講解的這個(gè)共享鎖實(shí)現(xiàn),大體上能夠滿足?般的分布式集群競(jìng)爭(zhēng)鎖的需求,并且性能都還可以—— 這?說(shuō)的?般場(chǎng)景是指集群規(guī)模不是特別大,?般是在10臺(tái)機(jī)器以內(nèi)。但是如果機(jī)器規(guī)模擴(kuò)大之后,會(huì)有什么問(wèn)題呢?我們著重來(lái)看上面“判斷讀寫順序”過(guò)程的步驟3,結(jié)合下面的圖,看看實(shí)際運(yùn)行中的情況zookeeper主流應(yīng)用場(chǎng)景有哪些,Zookeeper,java-zookeeper,zookeeper,分布式

針對(duì)如上圖所示的情況進(jìn)行分析

  1. host1?先進(jìn)行讀操作,完成后將節(jié)點(diǎn)/shared_lock/host1-R-00000001刪除
  2. 余下4臺(tái)機(jī)器均收到這個(gè)節(jié)點(diǎn)移除的通知,然后重新從/shared_lock節(jié)點(diǎn)上獲取?份新的子節(jié)點(diǎn)列表。
  3. 每臺(tái)機(jī)器判斷自己的讀寫順序,其中host2檢測(cè)到自己序號(hào)最小,于是進(jìn)行寫操作,余 下的機(jī)器則繼續(xù)等待
  4. 繼續(xù)…

可以看到,host1客戶端在移除自己的共享鎖后,Zookeeper發(fā)送了子節(jié)點(diǎn)更變Watcher通知給所有機(jī)器,然而除了給host2產(chǎn)?影響外,對(duì)其他機(jī)器沒(méi)有任何作用。大量的Watcher通知和子節(jié)點(diǎn)列表獲取兩個(gè)操作會(huì)重復(fù)運(yùn)行,這樣不僅會(huì)對(duì)zookeeper服務(wù)器造成巨大的性能影響影響和網(wǎng)絡(luò)開(kāi)銷,更為嚴(yán)重的是,如果同?時(shí)間有多個(gè)節(jié)點(diǎn)對(duì)應(yīng)的客戶端完成事務(wù)或是事務(wù)中斷引起節(jié)點(diǎn)消失,ZooKeeper服務(wù)器就會(huì)在短時(shí)間內(nèi)向其余客戶端發(fā)送大量的事件通知,這就是所謂的羊群效應(yīng)。 上面這個(gè)ZooKeeper分布式共享鎖實(shí)現(xiàn)中出現(xiàn)羊群效應(yīng)的根源在于,沒(méi)有找準(zhǔn)客戶端真正的關(guān)注點(diǎn)。我 們?cè)賮?lái)回顧?下上面的分布式鎖競(jìng)爭(zhēng)過(guò)程,它的核心邏輯在于:判斷自己是否是所有子節(jié)點(diǎn)中序號(hào)最小的。于是,很容易可以聯(lián)想到,每個(gè)節(jié)點(diǎn)對(duì)應(yīng)的客戶端只需要關(guān)注?自己序號(hào)小的那個(gè)相關(guān)節(jié)點(diǎn)的變更情況就可以了——而不需要關(guān)注全局的子列表變更情況。 可以有如下改動(dòng)來(lái)避免羊群效應(yīng)。

改進(jìn)后的分布式鎖實(shí)現(xiàn):

?先,我們需要肯定的?點(diǎn)是,上?提到的共享鎖實(shí)現(xiàn),從整體思路上來(lái)說(shuō)完全正確。這?主要的改動(dòng)在于:每個(gè)鎖競(jìng)爭(zhēng)者,只需要關(guān)注/shared_lock節(jié)點(diǎn)下序號(hào)?自己小的那個(gè)節(jié)點(diǎn)是否存在即可,具體實(shí)現(xiàn)如下。

  1. 客戶端調(diào)用create接?常?類似于/shared_lock/[Hostname]-請(qǐng)求類型-序號(hào)的臨時(shí)順序節(jié)點(diǎn)。
  2. 客戶端調(diào)用getChildren接?獲取所有已經(jīng)創(chuàng)建的子節(jié)點(diǎn)列表(不注冊(cè)任何Watcher)。
  3. 如果?法獲取共享鎖,就調(diào)用exist接?來(lái)對(duì)?自己小的節(jié)點(diǎn)注冊(cè)Watcher。對(duì)于讀請(qǐng)求:向?自己序號(hào)小的最后?個(gè)寫請(qǐng)求節(jié)點(diǎn)注冊(cè)Watcher監(jiān)聽(tīng)。對(duì)于寫請(qǐng)求:向?自己序號(hào)小的最后?個(gè)節(jié)點(diǎn)注冊(cè)Watcher監(jiān)聽(tīng)。
  4. 等待Watcher通知,繼續(xù)進(jìn)入步驟2。

此?案改動(dòng)主要在于:每個(gè)鎖競(jìng)爭(zhēng)者,只需要關(guān)注/shared_lock節(jié)點(diǎn)下序號(hào)?自己小的那個(gè)節(jié)點(diǎn)是否存在即可。

zookeeper主流應(yīng)用場(chǎng)景有哪些,Zookeeper,java-zookeeper,zookeeper,分布式

注意 相信很多同學(xué)都會(huì)覺(jué)得改進(jìn)后的分布式鎖實(shí)現(xiàn)相對(duì)來(lái)說(shuō)?較麻煩。確實(shí)如此,如同在多線程并發(fā)編程實(shí)踐中,我們會(huì)去盡量縮小鎖的范圍——對(duì)于分布式鎖實(shí)現(xiàn)的改進(jìn)其實(shí)也是同樣的思路。那么對(duì)于開(kāi)發(fā)人員來(lái)說(shuō),是否必須按照改進(jìn)后的思路來(lái)設(shè)計(jì)實(shí)現(xiàn)??的分布式鎖呢?答案是否定的。在具體的實(shí)際開(kāi)發(fā)過(guò)程中,我們提倡根據(jù)具體的業(yè)務(wù)場(chǎng)景和集群規(guī)模來(lái)選擇適合??的分布式鎖實(shí)現(xiàn):在集群規(guī)模不大、網(wǎng)絡(luò)資源豐富的情況下,第?種分布式鎖實(shí)現(xiàn)?式是簡(jiǎn)單實(shí)用的選擇;而如果集群規(guī)模達(dá)到?定程度,并且希望能夠精細(xì)化地控制分布式鎖機(jī)制,那么就可以試試改進(jìn)版的分布式鎖實(shí)現(xiàn)。

6. 布式隊(duì)列

分布式隊(duì)列可以簡(jiǎn)單分為兩大類:?種是常規(guī)的FIFO先入先出隊(duì)列模型,還有?種是等待隊(duì)列元素聚 集后統(tǒng)?安排處理執(zhí)行的Barrier模型。

6.1 FIFO先入先出

FIFO(First Input First Output,先?先出), FIFO 隊(duì)列是?種?常典型且應(yīng)用?泛的按序執(zhí)行的隊(duì)列 模型:先進(jìn)?隊(duì)列的請(qǐng)求操作先完成后,才會(huì)開(kāi)始處理后?的請(qǐng)求。

使用ZooKeeper實(shí)現(xiàn)FIFO隊(duì)列,和之前提到的共享鎖的實(shí)現(xiàn)?常類似。FIFO隊(duì)列就類似于?個(gè)全寫的共 享鎖模型,大體的設(shè)計(jì)思路其實(shí)?常簡(jiǎn)單:所有客戶端都會(huì)到/queue_fifo 這個(gè)節(jié)點(diǎn)下?創(chuàng)建?個(gè)臨時(shí) 順序節(jié)點(diǎn),例如如/queue_fifo/host1-00000001

zookeeper主流應(yīng)用場(chǎng)景有哪些,Zookeeper,java-zookeeper,zookeeper,分布式

創(chuàng)建完節(jié)點(diǎn)后,根據(jù)如下4個(gè)步驟來(lái)確定執(zhí)行順序。

  1. 通過(guò)調(diào)用getChildren接?來(lái)獲取/queue_fifo節(jié)點(diǎn)的所有子節(jié)點(diǎn),即獲取隊(duì)列中所有的元素。

  2. 確定??的節(jié)點(diǎn)序號(hào)在所有子節(jié)點(diǎn)中的順序。

  3. 如果??的序號(hào)不是最小,那么需要等待,同時(shí)向???序號(hào)小的最后?個(gè)節(jié)點(diǎn)注冊(cè)Watcher監(jiān)聽(tīng)。

  4. 接收到Watcher通知后,重復(fù)步驟1。

    zookeeper主流應(yīng)用場(chǎng)景有哪些,Zookeeper,java-zookeeper,zookeeper,分布式

6.2 Barrier:分布式屏障

Barrier原意是指障礙物、屏障,而在分布式系統(tǒng)中,特指系統(tǒng)之間的?個(gè)協(xié)調(diào)條件,規(guī)定了?個(gè)隊(duì)列的元素必須都集聚后才能統(tǒng)?進(jìn)行安排,否則?直等待。這往往出現(xiàn)在那些大規(guī)模分布式并行計(jì)算的應(yīng)用場(chǎng)景上:最終的合并計(jì)算需要基于很多并行計(jì)算的子結(jié)果來(lái)進(jìn)行。這些隊(duì)列其實(shí)是在 FIFO 隊(duì)列的基礎(chǔ)上進(jìn)行了增強(qiáng),大致的設(shè)計(jì)思想如下:開(kāi)始時(shí),/queue_barrier 節(jié)點(diǎn)是?個(gè)已經(jīng)存在的默認(rèn)節(jié)點(diǎn),并且將其節(jié)點(diǎn)的數(shù)據(jù)內(nèi)容賦值為?個(gè)數(shù)字n來(lái)代表Barrier值,例如n=10表示只有當(dāng)/queue_barrier節(jié)點(diǎn)下的子節(jié)點(diǎn)個(gè)數(shù)達(dá)到10后,才會(huì)打開(kāi)Barrier。之后,所有的客戶端都會(huì)到/queue_barrie節(jié)點(diǎn)下創(chuàng)建?個(gè)臨時(shí)節(jié)點(diǎn),例如/queue_barrier/host1,如圖所示。

zookeeper主流應(yīng)用場(chǎng)景有哪些,Zookeeper,java-zookeeper,zookeeper,分布式

創(chuàng)建完節(jié)點(diǎn)后,按照如下步驟執(zhí)?。

  1. 通過(guò)調(diào)?getData接?獲取/queue_barrier節(jié)點(diǎn)的數(shù)據(jù)內(nèi)容:10
  2. 通過(guò)調(diào)?getChildren接?獲取/queue_barrier節(jié)點(diǎn)下的所有子節(jié)點(diǎn),同時(shí)注冊(cè)對(duì)子節(jié)點(diǎn)變更的Watcher監(jiān)聽(tīng)。
  3. 統(tǒng)計(jì)子節(jié)點(diǎn)的個(gè)數(shù)。
  4. 如果子節(jié)點(diǎn)個(gè)數(shù)還不足10個(gè),那么需要等待。
  5. 接受到Wacher通知后,重復(fù)步驟2

zookeeper主流應(yīng)用場(chǎng)景有哪些,Zookeeper,java-zookeeper,zookeeper,分布式文章來(lái)源地址http://www.zghlxwxcb.cn/news/detail-722567.html

到了這里,關(guān)于Zookeeper六大應(yīng)用場(chǎng)景詳解的文章就介紹完了。如果您還想了解更多內(nèi)容,請(qǐng)?jiān)谟疑辖撬阉鱐OY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!

本文來(lái)自互聯(lián)網(wǎng)用戶投稿,該文觀點(diǎn)僅代表作者本人,不代表本站立場(chǎng)。本站僅提供信息存儲(chǔ)空間服務(wù),不擁有所有權(quán),不承擔(dān)相關(guān)法律責(zé)任。如若轉(zhuǎn)載,請(qǐng)注明出處: 如若內(nèi)容造成侵權(quán)/違法違規(guī)/事實(shí)不符,請(qǐng)點(diǎn)擊違法舉報(bào)進(jìn)行投訴反饋,一經(jīng)查實(shí),立即刪除!

領(lǐng)支付寶紅包贊助服務(wù)器費(fèi)用

相關(guān)文章

  • zookeeper應(yīng)用場(chǎng)景(二)

    zookeeper應(yīng)用場(chǎng)景(二)

    單機(jī)環(huán)境下可以利用jvm級(jí)別的鎖,比如synchronized、Lock等來(lái)實(shí)現(xiàn)鎖,如果是多機(jī)部署就需要一個(gè)共享數(shù)據(jù)存儲(chǔ)區(qū)域來(lái)實(shí)現(xiàn)分布式鎖 1、基于數(shù)據(jù)庫(kù)實(shí)現(xiàn)分布式鎖 可以用數(shù)據(jù)庫(kù)唯一索引來(lái)實(shí)現(xiàn) 2、基于redis實(shí)現(xiàn)分布式鎖 redis實(shí)現(xiàn)的分布式鎖始終會(huì)有一些問(wèn)題,即便使用多數(shù)寫入,

    2024年02月07日
    瀏覽(26)
  • Zookeeper的應(yīng)用場(chǎng)景

    Zookeeper的應(yīng)用場(chǎng)景

    配置中心:Zookeeper可以用來(lái)存儲(chǔ)和管理配置信息,例如集群中的機(jī)器配置、服務(wù)地址配置等。通過(guò)Zookeeper,可以將配置信息統(tǒng)一管理,同時(shí)實(shí)現(xiàn)動(dòng)態(tài)加載和更新。 統(tǒng)一命名服務(wù):Zookeeper可以用來(lái)實(shí)現(xiàn)命名服務(wù),例如將集群中的機(jī)器名稱和IP地址進(jìn)行映射,或者將服務(wù)的唯一標(biāo)

    2024年02月15日
    瀏覽(20)
  • Zookeeper經(jīng)典應(yīng)用場(chǎng)景實(shí)戰(zhàn)(一)

    Zookeeper經(jīng)典應(yīng)用場(chǎng)景實(shí)戰(zhàn)(一)

    ZooKeeper應(yīng)用的開(kāi)發(fā)主要通過(guò)Java客戶端API去連接和操作ZooKeeper集群。 可供選擇的Java客戶端API有: ZooKeeper官方的Java客戶端API。 第三方的Java客戶端API,比如Curator。 ZooKeeper官方的客戶端API提供了基本的操作。例如,創(chuàng)建會(huì)話、創(chuàng)建節(jié)點(diǎn)、讀取節(jié)點(diǎn)、更新數(shù)據(jù)、刪除節(jié)點(diǎn)和檢查節(jié)

    2024年02月09日
    瀏覽(25)
  • ZooKeeper的典型應(yīng)用場(chǎng)景及實(shí)現(xiàn)

    ZooKeeper的典型應(yīng)用場(chǎng)景及實(shí)現(xiàn)

    ZooKeeper是一個(gè)典型的發(fā)布/訂閱模式的分布式數(shù)據(jù)管理與協(xié)調(diào)框架,開(kāi)發(fā)人員可以使用它來(lái)進(jìn)行分布式數(shù)據(jù)的發(fā)布與訂閱。另一方面,通過(guò)對(duì)ZooKeeper中豐富的數(shù)據(jù)節(jié)點(diǎn)類型進(jìn)行交叉使用,配合Watcher事件通知機(jī)制,可以非常方便地構(gòu)建一系列分布式應(yīng)用中都會(huì)涉及的核心功能,

    2024年02月10日
    瀏覽(15)
  • ZooKeeper客戶端使用與經(jīng)典應(yīng)用場(chǎng)景

    ZooKeeper的應(yīng)用場(chǎng)景依賴于ZNode節(jié)點(diǎn)特性和Watch監(jiān)聽(tīng)機(jī)制。 常用于實(shí)現(xiàn)配置中心,類似的有nacos。 數(shù)據(jù)發(fā)布/訂閱的一個(gè)常見(jiàn)的場(chǎng)景是配置中心,發(fā)布者把數(shù)據(jù)發(fā)布到ZooKeeper的一個(gè)或一系列的節(jié)點(diǎn)上,供訂閱者進(jìn)行數(shù)據(jù)訂閱,達(dá)到動(dòng)態(tài)獲取數(shù)據(jù)的目的。 配置信息一般有幾個(gè)特點(diǎn)

    2024年02月12日
    瀏覽(22)
  • ZooKeeper的應(yīng)用場(chǎng)景(集群管理、Master選舉)

    ZooKeeper的應(yīng)用場(chǎng)景(集群管理、Master選舉)

    隨著分布式系統(tǒng)規(guī)模的日益擴(kuò)大,集群中的機(jī)器規(guī)模也隨之變大,因此,如何更好地進(jìn)行集群管理也顯得越來(lái)越重要了。 所謂集群管理,包括集群監(jiān)控與集群控制兩大塊,前者側(cè)重對(duì)集群運(yùn)行時(shí)狀態(tài)的收集,后者則是對(duì)集群進(jìn)行操作與控制。在日常開(kāi)發(fā)和運(yùn)維過(guò)程中,我們經(jīng)

    2024年02月12日
    瀏覽(24)
  • 【大廠面試演練】知道ZooKeeper有什么應(yīng)用場(chǎng)景嗎

    【大廠面試演練】知道ZooKeeper有什么應(yīng)用場(chǎng)景嗎

    面試官:咳咳咳,看你簡(jiǎn)歷寫了精通ZooKeeper,那我就隨便考考你吧 面試官:不用慌盡管說(shuō),錯(cuò)了也沒(méi)關(guān)系??。。。 每日分享大廠面試演練,感興趣就關(guān)注我吧 ?? 嗯嗯,主要有這幾種。 數(shù)據(jù)發(fā)布/訂閱??梢杂脕?lái)實(shí)現(xiàn)配置中心 命名服務(wù)。類似于UUID,可以生成全局唯一的

    2024年03月15日
    瀏覽(32)
  • ZooKeeper的應(yīng)用場(chǎng)景(命名服務(wù)、分布式協(xié)調(diào)通知)

    ZooKeeper的應(yīng)用場(chǎng)景(命名服務(wù)、分布式協(xié)調(diào)通知)

    命名服務(wù)(NameService)也是分布式系統(tǒng)中比較常見(jiàn)的一類場(chǎng)景,在《Java網(wǎng)絡(luò)高級(jí)編程》一書中提到,命名服務(wù)是分布式系統(tǒng)最基本的公共服務(wù)之一。在分布式系統(tǒng)中,被命名的實(shí)體通??梢允羌褐械臋C(jī)器、提供的服務(wù)地址或遠(yuǎn)程對(duì)象等一這些我們都可以統(tǒng)稱它們?yōu)槊?Name),

    2024年02月12日
    瀏覽(94)
  • zookeeper應(yīng)用場(chǎng)景之分布式的ID生成器

    zookeeper應(yīng)用場(chǎng)景之分布式的ID生成器

    ????????在分布式系統(tǒng)中, 分布式ID生成器的使用場(chǎng)景非常之多 : 大量的數(shù)據(jù)記錄,需要分布式ID。 大量的系統(tǒng)消息,需要分布式ID。 大量的請(qǐng)求日志,如restful的操作記錄,需要唯一標(biāo)識(shí),以便進(jìn)行后續(xù)的用戶行為分析和調(diào)用鏈路分析。 分布式節(jié)點(diǎn)的命名服務(wù),往往也

    2024年01月23日
    瀏覽(33)
  • 詳解ZooKeeper在微服務(wù)注冊(cè)中心的應(yīng)用

    本文分享自華為云社區(qū)《SpringCloud ZooKeeper 詳解,以及與Go、Rust等非Java服務(wù)的集成》,作者: 張儉。 ZooKeeper,是一個(gè)開(kāi)源的分布式協(xié)調(diào)服務(wù),不僅支持分布式選舉、任務(wù)分配,還可以用于微服務(wù)的注冊(cè)中心和配置中心。本文,我們將深入探討ZooKeeper用做微服務(wù)注冊(cè)中心的場(chǎng)景

    2024年01月25日
    瀏覽(19)

覺(jué)得文章有用就打賞一下文章作者

支付寶掃一掃打賞

博客贊助

微信掃一掃打賞

請(qǐng)作者喝杯咖啡吧~博客贊助

支付寶掃一掃領(lǐng)取紅包,優(yōu)惠每天領(lǐng)

二維碼1

領(lǐng)取紅包

二維碼2

領(lǐng)紅包