03.20 大話微服務之服務治理框架的比較-Zookeeper vs etcd vs Consul

如果使用預定義的端口,服務越多,發生衝突的可能性越大,畢竟,不可能有兩個服務監聽同一個端口。管理一個擁擠的比方說被幾百個服務所使用的所有端口的列表,本身就是一個挑戰,添加到該列表後,這些服務需要的數據庫和數量會日益增多。因此我們應該部署無需指定端口的服務,並且讓Docker為我們分配一個隨機的端口。唯一的問題是我們需要發現端口號,並且讓別人知道。

大話微服務之服務治理框架的比較-Zookeeper vs etcd vs Consul

當我們開始在一個分佈式系統上部署服務到其中一臺服務器上時,事情會變得更加複雜,我們可以選擇預先定義哪臺服務器運行哪個服務的方式,但這會導致很多問題。我們應該盡我們所能儘量利用服務器資源,但是如果預先定義每個服務的部署位置,那麼要實現儘量利用服務器資源是幾乎不可能的。另一個問題是服務的自動伸縮將會非常困難,更不用說自動恢復了,比方說服務器故障。另一方面,如果我們將服務部署到某臺只有最少數量的容器在運行的服務器上,我們需要添加IP地址到數據列表中,這些數據需要可以被發現並存儲在某處。

大話微服務之服務治理框架的比較-Zookeeper vs etcd vs Consul

當我們需要存儲和發現一些與正在工作的服務相關的信息時,還有很多其他的例子。

為了能夠定位服務,我們需要至少接下來的兩個有用的步驟。

  • 服務註冊——該步驟存儲的信息至少包括正在運行的服務的主機和端口信息

  • 服務發現——該步驟允許其他用戶可以發現在服務註冊階段存儲的信息。

除了上述的步驟,我們還需要考慮其他方面。如果一個服務停止工作並部署/註冊了一個新的服務實例,那麼該服務是否應該註銷呢?當有相同服務的多個副本時咋辦?我們該如何做負載均衡呢?如果一個服務器宕機了咋辦?所有這些問題都與註冊和發現階段緊密關聯。現在,我們限定只在服務發現的範圍裡(常見的名字,圍繞上述步驟)以及用於服務發現任務的工具,它們中的大多數採用了高可用的分佈式鍵/值存儲。

服務發現工具

服務發現工具的主要目標是用來服務查找和相互對話,為此該工具需要知道每個服務,這不是一個新概念,在Docker之前就已經存在很多類似的工具了,然而,容器帶給了這些工具一個全新水平的需求。

服務發現背後的基本思想是對於服務的每一個新實例(或應用程序),能夠識別當前環境和存儲相關信息。存儲的註冊表信息本身通常採用鍵/值對的格式,由於服務發現經常用於分佈式系統,所以要求這些信息可伸縮、支持容錯和分佈式集群中的所有節點。這種存儲的主要用途是給所有感興趣的各方提供最起碼諸如服務IP地址和端口這樣的信息,用於它們之間的相互通訊,這些數據還經常擴展到其它類型的信息服務發現工具傾向於提供某種形式的API,用於服務自身的註冊以及服務信息的查找。

比方說我們有兩個服務,一個是提供方,另一個是第一個服務的消費者,一旦部署了服務提供方,就需要在服務發現註冊表中存儲其信息。接著,當消費者試圖訪問服務提供者時,它首先查詢服務註冊表,使用獲取到的IP地址和端口來調用服務提供者。為了與註冊表中的服務提供方的具體實現解耦,我們常常採用某種代理服務。這樣消費者總是向固定IP地址的代理請求信息,代理再依次使用服務發現來查找服務提供方信息並重定向請求,在本文中我們稍後通過反向代理來實現。現在重要的是要理解基於三種角色(服務消費者、提供者和代理)的服務發現流程。

服務發現工具要查找的是數據,至少我們應該能夠找出服務在哪裡?服務是否健康和可用?配置是什麼樣的?既然我們正在多臺服務器上構建一個分佈式系統,那麼該工具需要足夠健壯,保證其中一個節點的宕機不會危及數據,同時,每個節點應該有完全相同的數據副本,進一步地,我們希望能夠以任何順序啟動服務、殺死服務或者替換服務的新版本,我們還應該能夠重新配置服務並且查看到數據相應的變化。

讓我們看一下一些常用的選項來完成我們上面設定的目標。

手動配置

大多數服務仍然是需要手動管理的,我們預先決定在何處部署服務、如何配置和希望不管什麼原因,服務都將繼續正常工作,直到天荒地老。這樣的目標不是可以輕易達到的。部署第二個服務實例意味著我們需要啟動全程的手動處理,我們需要引入一臺新的服務器,或者找出哪一臺服務器資源利用率較低,然後創建一個新的配置集並啟動服務。情況或許會變得越來越複雜,比方說,硬件故障導致的手動管理下的反應時間變得很慢。可見性是另外一個痛點,我們知道什麼是靜態配置,畢竟是我們預先準備好的,然而,大多數的服務有很多動態生成的信息,這些信息不是輕易可見的,也沒有一個單獨的地方供我們在需要時參考這些數據。

反應時間會不可避免的變慢,鑑於存在許多需要手動處理的移動組件,故障恢復和監控也會變得非常難以管理。

儘管在過去或者當服務/服務器數量很少的時候有藉口不做這項工作,隨著服務發現工具的出現,這個藉口已經不存在了。

Zookeeper

Zookeeper是這種類型的項目中歷史最悠久的之一,它起源於Hadoop,幫助在Hadoop集群中維護各種組件。它非常成熟、可靠,被許多大公司(YouTube、eBay、雅虎等)使用。其數據存儲的格式類似於文件系統,如果運行在一個服務器集群中,Zookeper將跨所有節點共享配置狀態,每個集群選舉一個領袖,客戶端可以連接到任何一臺服務器獲取數據。

Zookeeper的主要優勢是其成熟、健壯以及豐富的特性,然而,它也有自己的缺點,其中採用Java開發以及複雜性是罪魁禍首。儘管Java在許多方面非常偉大,然後對於這種類型的工作還是太沉重了,Zookeeper使用Java以及相當數量的依賴使其對於資源競爭非常飢渴。因為上述的這些問題,Zookeeper變得非常複雜,維護它需要比我們期望從這種類型的應用程序中獲得的收益更多的知識。這部分地是由於豐富的特性反而將其從優勢轉變為累贅。應用程序的特性功能越多,就會有越大的可能性不需要這些特性,因此,我們最終將會為這些不需要的特性付出複雜度方面的代價。

Zookeeper為其他項目相當大的改進鋪平了道路,“大數據玩家“在使用它,因為沒有更好的選擇。今天,Zookeeper已經老態龍鍾了,我們有了更好的選擇。

etcd

etcd是一個採用HTTP協議的健/值對存儲系統,它是一個分佈式和功能層次配置系統,可用於構建服務發現系統。其很容易部署、安裝和使用,提供了可靠的數據持久化特性。它是安全的並且文檔也十分齊全。

etcd比Zookeeper是比更好的選擇,因為它很簡單,然而,它需要搭配一些第三方工具才可以提供服務發現功能。

大話微服務之服務治理框架的比較-Zookeeper vs etcd vs Consul

現在,我們有一個地方來存儲服務相關信息,我們還需要一個工具可以自動發送信息給etcd。但在這之後,為什麼我們還需要手動把數據發送給etcd呢?即使我們希望手動將信息發送給etcd,我們通常情況下也不會知道是什麼信息。記住這一點,服務可能會被部署到一臺運行最少數量容器的服務器上,並且隨機分配一個端口。理想情況下,這個工具應該監視所有節點上的Docker容器,並且每當有新容器運行或者現有的一個容器停止的時候更新etcd,其中的一個可以幫助我們達成目標的工具就是Registrator。

Registrator

Registrator通過檢查容器在線或者停止運行狀態自動註冊和去註冊服務,它目前支持etcd、Consul和SkyDNS 2。

Registrator與etcd是一個簡單但是功能強大的組合,可以運行很多先進的技術。每當我們打開一個容器,所有數據將被存儲在etcd並傳播到集群中的所有節點。我們將決定什麼信息是我們的。

大話微服務之服務治理框架的比較-Zookeeper vs etcd vs Consul

上述的拼圖遊戲還缺少一塊,我們需要一種方法來創建配置文件,與數據都存儲在etcd,通過運行一些命令來創建這些配置文件。

Confd

Confd是一個輕量級的配置管理工具,常見的用法是通過使用存儲在etcd、consul和其他一些數據登記處的數據保持配置文件的最新狀態,它也可以用來在配置文件改變時重新加載應用程序。換句話說,我們可以用存儲在etcd(或者其他註冊中心)的信息來重新配置所有服務。

大話微服務之服務治理框架的比較-Zookeeper vs etcd vs Consul

對於etcd、Registrator和Confd組合的最後的思考

當etcd、Registrator和Confd結合時,可以獲得一個簡單而強大的方法來自動化操作我們所有的服務發現和需要的配置。這個組合還展示了“小”工具正確組合的有效性,這三個小東西可以如我們所願正好完成我們需要達到的目標,若範圍稍微小一些,我們將無法完成我們面前的目標,而另一方面如果他們設計時考慮到更大的範圍,我們將引入不必要的複雜性和服務器資源開銷。

在我們做出最後的判決之前,讓我們看看另一個有相同目標的工具組合,畢竟,我們不應該滿足於一些沒有可替代方案的選擇。

Consul

Consul是強一致性的數據存儲,使用gossip形成動態集群。它提供分級鍵/值存儲方式,不僅可以存儲數據,而且可以用於註冊器件事各種任務,從發送數據改變通知到運行健康檢查和自定義命令,具體如何取決於它們的輸出。

與Zookeeper和etcd不一樣,Consul內嵌實現了服務發現系統,所以這樣就不需要構建自己的系統或使用第三方系統。這一發現系統除了上述提到的特性之外,還包括節點健康檢查和運行在其上的服務。

Zookeeper和etcd只提供原始的鍵/值隊存儲,要求應用程序開發人員構建他們自己的系統提供服務發現功能。而Consul提供了一個內置的服務發現的框架。客戶只需要註冊服務並通過DNS或HTTP接口執行服務發現。其他兩個工具需要一個親手製作的解決方案或藉助於第三方工具。

Consul為多種數據中心提供了開箱即用的原生支持,其中的gossip系統不僅可以工作在同一集群內部的各個節點,而且還可以跨數據中心工作。

大話微服務之服務治理框架的比較-Zookeeper vs etcd vs Consul

Consul還有另一個不錯的區別於其他工具的功能,它不僅可以用來發現已部署的服務以及其駐留的節點信息,還通過HTTP請求、TTLs(time-to-live)和自定義命令提供了易於擴展的健康檢查特性。

Registrator

Registrator有兩個Consul協議,其中consulkv協議產生類似於etcd協議的結果。

除了通常的IP和端口存儲在etcd或consulkv協議中之外,Registrator consul協議存儲了更多的信息,我們可以得到服務運行節點的信息,以及服務ID和名稱。我們也可以藉助於一些額外的環境變量按照一定的標記存儲額外的信息。

大話微服務之服務治理框架的比較-Zookeeper vs etcd vs Consul

Consul-template

confd可以像和etce搭配一樣用於Consul,不過Consul有自己的模板服務,其更適配Consul。

通過從Consul獲得的信息,Consul-template是一個非常方便的創建文件的途徑,還有一個額外的好處就是在文件更新後可以運行任意命令,正如confd,Consul-template也可以使用Go模板格式。

大話微服務之服務治理框架的比較-Zookeeper vs etcd vs Consul

Consul健康檢查、Web界面和數據中心

監控集群節點和服務的健康狀態與測試和部署它們一樣的重要。雖然我們應該向著擁有從來沒有故障的穩定的環境努力,但我們也應該承認,隨時會有意想不到的故障發生,時刻準備著採取相應的措施。例如我們可以監控內存使用情況,如果達到一定的閾值,那麼遷移一些服務到集群中的另外一個節點,這將是在發生“災難”前執行的一個預防措施。另一方面,並不是所有潛在的故障都可以被及時檢測到並採取措施。單個服務可能會齒白,一個完整的節點也可能由於硬件故障而停止工作。在這種情況下我們應該準備儘快行動,例如一個節點替換為一個新的並遷移失敗的服務。Consul有一個簡單的、優雅的但功能強大的方式進行健康檢查,當健康閥值達到一定數目時,幫助用戶定義應該執行的操作。

如果用戶Google搜索“etcd ui”或者“etec dashboard”時,用戶可能看到只有幾個可用的解決方案,可能會問為什麼我們還沒有介紹給用戶,這個原因很簡單,etcd只是鍵/值對存儲,僅此而已。通過一個UI呈現數據沒有太多的用處,因為我們可以很容易地通過etcdctl獲得這些數據。這並不意味著etcd UI是無用的,但鑑於其有限的使用範圍,它不會產生多大影響。

Consu不僅僅是一個簡單的鍵/值對存儲,正如我們已經看到的,除了存儲簡單的鍵/值對,它還有一個服務的概念以及所屬的數據。它還可以執行健康檢查,因此成為一個好的候選dashboard,在上面可以看到我們的節點的狀態和運行的服務。最後,它支持了多數據中心的概念。所有這些特性的結合讓我們從不同的角度看到引入dashboard的必要性。

通過Consul Web界面,用戶可以查看所有的服務和節點、監控健康檢查狀態以及通過切換數據中心讀取設置鍵/值對數據。

大話微服務之服務治理框架的比較-Zookeeper vs etcd vs Consul

對於Consul、Registrator、Template、健康檢查和Web UI的最終思考

Consul以及上述我們一起探討的工具在很多情況下提供了比etcd更好的解決方案。這是從內心深處為了服務架構和發現而設計的方案,簡單而強大。它提供了一個完整的同時不失簡潔的解決方案,在許多情況下,這是最佳的服務發現以及滿足健康檢查需求的工具。

結論

所有這些工具都是基於相似的原則和架構,它們在節點上運行,需要仲裁來運行,並且都是強一致性的,都提供某種形式的鍵/值對存儲。

Zookeeper是其中最老態龍鍾的一個,使用年限顯示出了其複雜性、資源利用和盡力達成的目標,它是為了與我們評估的其他工具所處的不同時代而設計的(即使它不是老得太多)。

etcd、Registrator和Confd是一個非常簡單但非常強大的組合,可以解決大部分問題,如果不是全部滿足服務發現需要的話。它還展示了我們可以通過組合非常簡單和特定的工具來獲得強大的服務發現能力,它們中的每一個都執行一個非常具體的任務,通過精心設計的API進行通訊,具備相對自治工作的能力,從架構和功能途徑方面都是微服務方式。

Consul的不同之處在於無需第三方工具就可以原生支持多數據中心和健康檢查,這並不意味著使用第三方工具不好。實際上,在這篇博客裡我們通過選擇那些表現更佳同時不會引入不必要的功能的的工具,盡力組合不同的工具。使用正確的工具可以獲得最好的結果。如果工具引入了工作不需要的特性,那麼工作效率反而會下降,另一方面,如果工具沒有提供工作所需要的特性也是沒有用的。Consul很好地權衡了權重,用盡量少的東西很好的達成了目標。

Consul使用gossip來傳播集群信息的方式,使其比etcd更易於搭建,特別是對於大的數據中心。將存儲數據作為服務的能力使其比etcd僅僅只有健/值對存儲的特性更加完整、更有用(即使Consul也有該選項)。雖然我們可以在etcd中通過插入多個鍵來達成相同的目標,Consul的服務實現了一個更緊湊的結果,通常只需要一次查詢就可以獲得與服務相關的所有數據。除此之外,Registrator很好地實現了Consul的兩個協議,使其合二為一,特別是添加Consul-template到了拼圖中。Consul的Web UI更是錦上添花般地提供了服務和健康檢查的可視化途徑。

我不能說Consul是一個明確的贏家,而是與etcd相比其有一個輕微的優勢。服務發現作為一個概念,以及作為工具都很新,我們可以期待在這一領域會有許多的變化。秉承開放的心態,大家可以對本文的建議持保留態度,嘗試不同的工具然後做出自己的結論。


分享到:


相關文章: