更新時間:2020-10-30 來源:黑馬程序員 瀏覽量:
隨著分布式系統(tǒng)規(guī)模的日益擴(kuò)大,集群中的機器規(guī)模也隨之變大,那如何更好地進(jìn)行集群管理也顯得越來越重要了。所謂集群管理,包括集群監(jiān)控與集群控制兩大塊,前者側(cè)重對集群運行時狀態(tài)的收集,后者則是對集群進(jìn)行操作與控制。
在日常開發(fā)和運維過程中,我們經(jīng)常會有類似于如下的需求:
·如何快速的統(tǒng)計出當(dāng)前生產(chǎn)環(huán)境下一共有多少臺機器
·如何快速的獲取到機器上下線的情況
·如何實時監(jiān)控集群中每臺主機的運行時狀態(tài)
在傳統(tǒng)的基于Agent的分布式集群管理體系中,都是通過在集群中的每臺機器上部署一個 Agent,由這個 Agent
負(fù)責(zé)主動向指定的一個監(jiān)控中心系統(tǒng)(監(jiān)控中心系統(tǒng)負(fù)責(zé)將所有數(shù)據(jù)進(jìn)行集中處理,形成一系列報表,并負(fù)責(zé)實時報警,以下簡稱“監(jiān)控中心”)匯報自己所在機器的狀態(tài)。在集群規(guī)模適中的場景下,這確實是一種在生產(chǎn)實踐中廣泛使用的解決方案,能夠快速有效地實現(xiàn)分布式環(huán)境集群監(jiān)控,但是一旦系統(tǒng)的業(yè)務(wù)場景增多,集群規(guī)模變大之后,該解決方案的弊端也就顯現(xiàn)出來了。
大規(guī)模升級困難
以客戶端形式存在的 Agent,在大規(guī)模使用后,一旦遇上需要大規(guī)模升級的情況,就非常麻煩,在升級成本和升級進(jìn)度的控制上面臨巨大的挑戰(zhàn)。
統(tǒng)一的Agent無法滿足多樣的需求
對于機器的CPU使用率、負(fù)載(Load)、內(nèi)存使用率、網(wǎng)絡(luò)吞吐以及磁盤容量等機器基本的物理狀態(tài),使用統(tǒng)一的Agent來進(jìn)行監(jiān)控或許都可以滿足。但是,如果需要深入應(yīng)用內(nèi)部,對一些業(yè)務(wù)狀態(tài)進(jìn)行監(jiān)控,例如,在一個分布式消息中間件中,希望監(jiān)控到每個消費者對消息的消費狀態(tài);或者在一個分布式任務(wù)調(diào)度系統(tǒng)中,需要對每個機器上任務(wù)的執(zhí)行情況進(jìn)行監(jiān)控。很顯然,對于這些業(yè)務(wù)耦合緊密的監(jiān)控需求,不適合由一個統(tǒng)一的Agent來提供。
編程語言多樣性
隨著越來越多編程語言的出現(xiàn),各種異構(gòu)系統(tǒng)層出不窮。如果使用傳統(tǒng)的Agent方式,那么需要提供各種語言的 Agent
客戶端。另一方面,“監(jiān)控中心”在對異構(gòu)系統(tǒng)的數(shù)據(jù)進(jìn)行整合上面臨巨大挑戰(zhàn)。
Zookeeper的兩大特性:
1.客戶端如果對Zookeeper的數(shù)據(jù)節(jié)點注冊Watcher監(jiān)聽,那么當(dāng)該數(shù)據(jù)節(jié)點的內(nèi)容或是其子節(jié)點列表發(fā)生變更時,Zookeeper服務(wù)器就會向訂閱的客戶端發(fā)送變更通知。
2.對在Zookeeper上創(chuàng)建的臨時節(jié)點,一旦客戶端與服務(wù)器之間的會話失效,那么臨時節(jié)點也會被自動刪除
利用其兩大特性,可以實現(xiàn)集群機器存活監(jiān)控系統(tǒng),若監(jiān)控系統(tǒng)在/clusterServers節(jié)點上注冊一個Watcher監(jiān)聽,那么但凡進(jìn)行動態(tài)添加機器的操作,就會在/clusterServers節(jié)點下創(chuàng)建一個臨時節(jié)點:/clusterServers/[Hostname],這樣,監(jiān)控系統(tǒng)就能夠?qū)崟r監(jiān)測機器的變動情況。
下面通過分布式日志收集系統(tǒng)這個典型應(yīng)用來學(xué)習(xí)Zookeeper如何實現(xiàn)集群管理。
分布式日志收集系統(tǒng):
分布式日志收集系統(tǒng)的核心工作就是收集分布在不同機器上的系統(tǒng)日志,在這里我們重點來看分布式日志系統(tǒng)(以下簡稱“日志系統(tǒng)”)的收集器模塊。
在一個典型的日志系統(tǒng)的架構(gòu)設(shè)計中,整個日志系統(tǒng)會把所有需要收集的日志機器(我們以“日志源機器”代表此類機器)分為多個組別,每個組別對應(yīng)一個收集器,這個收集器其實就是一個后臺機器(我們以“收集器機器”代表此類機器),用于收集日志
· 變化的日志源機器
在生產(chǎn)環(huán)境中,伴隨著機器的變動,每個應(yīng)用的機器幾乎每天都是在變化的(機器硬件問題、擴(kuò)容、機房遷移或是網(wǎng)絡(luò)問題等都會導(dǎo)致一個應(yīng)用的機器變化),也就是說每個組別中的日志源機器通常是在不斷變化的。
· 變化的收集器機器
日志收集系統(tǒng)自身也會有機器的變更或擴(kuò)容,于是會出現(xiàn)新的收集器機器加入或是老的收集器機器退出的情況。
無論是日志源機器還是收集器機器的變更,最終都可以歸結(jié)為如何快速、合理、動態(tài)地為每個收集器分配對應(yīng)的日志源機器。這也成為了整個日志系統(tǒng)正確穩(wěn)定運轉(zhuǎn)的前提,也是日志收集過程中最大的技術(shù)挑戰(zhàn)之一,在這種情況下,我們就可以引入zookeeper了,下面我們就來看ZooKeeper在這個場景中的使用。
使用Zookeeper的場景步驟如下
① 注冊收集器機器
使用ZooKeeper來進(jìn)行日志系統(tǒng)收集器的注冊,典型做法是在ZooKeeper上創(chuàng)建一個節(jié)點作為收集器的根節(jié)點,例如/logs/collector(下文我們以“收集器節(jié)點”代表該數(shù)據(jù)節(jié)點),每個收集器機器在啟動的時候,都會在收集器節(jié)點下創(chuàng)建自己的節(jié)點,例如/logs/collector/[Hostname]
② 任務(wù)分發(fā)
待所有收集器機器都創(chuàng)建好自己對應(yīng)的節(jié)點后,系統(tǒng)根據(jù)收集器節(jié)點下子節(jié)點的個數(shù),將所有日志源機器分成對應(yīng)的若干組,然后將分組后的機器列表分別寫到這些收集器機器創(chuàng)建的子節(jié)點(例如/logs/collector/host1)上去。這樣一來,每個收集器機器都能夠從自己對應(yīng)的收集器節(jié)點上獲取日志源機器列表,進(jìn)而開始進(jìn)行日志收集工作。
③ 狀態(tài)匯報
完成收集器機器的注冊以及任務(wù)分發(fā)后,我們還要考慮到這些機器隨時都有掛掉的可能。因此,針對這個問題,我們需要有一個收集器的狀態(tài)匯報機制:每個收集器機器在創(chuàng)建完自己的專屬節(jié)點后,還需要在對應(yīng)的子節(jié)點上創(chuàng)建一個狀態(tài)子節(jié)點,例如/logs/collector/host1/status,每個收集器機器都需要定期向該節(jié)點寫入自己的狀態(tài)信息。我們可以把這種策略看作是一種心跳檢測機制,通常收集器機器都會在這個節(jié)點中寫入日志收集進(jìn)度信息。日志系統(tǒng)根據(jù)該狀態(tài)子節(jié)點的最后更新時間來判斷對應(yīng)的收集器機器是否存活。
④ 動態(tài)分配
如果收集器機器掛掉或是擴(kuò)容了,就需要動態(tài)地進(jìn)行收集任務(wù)的分配。在運行過程中,日志系統(tǒng)始終關(guān)注著/logs/collector這個節(jié)點下所有子節(jié)點的變更,一旦檢測到有收集器機器停止匯報或是有新的收集器機器加入,就要開始進(jìn)行任務(wù)的重新分配。無論是針對收集器機器停止匯報還是新機器加入的情況,日志系統(tǒng)都需要將之前分配給該收集器的所有任務(wù)進(jìn)行轉(zhuǎn)移。為了解決這個問題,通常有兩種做法:
· 全局動態(tài)分配
這是一種簡單粗暴的做法,在出現(xiàn)收集器機器掛掉或是新機器加入的時候,日志系統(tǒng)需要根據(jù)新的收集器機器列表,立即對所有的日志源機器重新進(jìn)行一次分組,然后將其分配給剩下的收集器機器。
· 局部動態(tài)分配
全局動態(tài)分配方式雖然策略簡單,但是存在一個問題:一個或部分收集器機器的變更,就會導(dǎo)致全局動態(tài)任務(wù)的分配,影響面比較大,因此風(fēng)險也就比較大。所謂局部動態(tài)分配,顧名思義就是在小范圍內(nèi)進(jìn)行任務(wù)的動態(tài)分配。在這種策略中,每個收集器機器在匯報自己日志收集狀態(tài)的同時,也會把自己的負(fù)載匯報上去。請注意,這里提到的負(fù)載并不僅僅只是簡單地指機器CPU負(fù)載(Load),而是一個對當(dāng)前收集器任務(wù)執(zhí)行的綜合評估,這個評估算法和ZooKeeper本身并沒有太大的關(guān)系,這里不再贅述。
在這種策略中,如果一個收集器機器掛了,那么日志系統(tǒng)就會把之前分配給這個機器的任務(wù)重新分配到那些負(fù)載較低的機器上去。同樣,如果有新的收集器機器加入,會從那些負(fù)載高的機器上轉(zhuǎn)移部分任務(wù)給這個新加入的機器。
上述步驟已經(jīng)完整的說明了整個日志收集系統(tǒng)的工作流程,其中有兩點注意事項:
①節(jié)點類型
在/logs/collector節(jié)點下創(chuàng)建臨時節(jié)點可以很好的判斷機器是否存活,但是,若機器掛了,其節(jié)點會被刪除,記錄在節(jié)點上的日志源機器列表也被清除,所以需要選擇持久節(jié)點來標(biāo)識每一臺機器,同時在節(jié)點下分別創(chuàng)建/logs/collector/[Hostname]/status節(jié)點來表征每一個收集器機器的狀態(tài),這樣,既能實現(xiàn)對所有機器的監(jiān)控,同時機器掛掉后,依然能夠?qū)⒎峙淙蝿?wù)還原。
② 日志系統(tǒng)節(jié)點監(jiān)聽
若采用Watcher機制,那么通知的消息量的網(wǎng)絡(luò)開銷非常大,需要采用日志系統(tǒng)主動輪詢收集器節(jié)點的策略,這樣可以節(jié)省網(wǎng)絡(luò)流量,但是存在一定的延時。
猜你喜歡
ZooKeeper數(shù)據(jù)發(fā)布/訂閱使用教程