從 Elasticsearch 來看分佈式系統架構設計

來源 | zhuanlan.zhihu.com/p/33375126

分佈式系統類型多,涉及面非常廣,不同類型的系統有不同的特點,批量計算和實時計算就差別非常大。這篇文章中,重點會討論下分佈式數據系統的設計,比如分佈式存儲系統,分佈式搜索系統,分佈式分析系統等。

我們先來簡單看下 Elasticsearch 的架構。

Elasticsearch 集羣架構

Elasticsearch 是一個非常著名的開源搜索和分析系統,目前被廣泛應用於互聯網多種領域中,尤其是以下三個領域特別突出。一是搜索領域,相對於 solr,真正的後起之秀,成爲很多搜索系統的不二之選。二是 Json 文檔數據庫,相對於 MongoDB,讀寫性能更佳,而且支持更豐富的地理位置查詢以及數字、文本的混合查詢等。三是時序數據分析處理,目前是日誌處理、監控數據的存儲、分析和可視化方面做得非常好,可以說是該領域的引領者了。

Elasticsearch 的詳細介紹可以到官網查看。我們先來看一下 Elasticsearch 中幾個關鍵概念:

用圖形表示出來可能是這樣子的:

圖片

Index 流程

建索引(Index)的時候,一個 Doc 先是經過路由規則定位到主 Shard,發送這個 doc 到主 Shard 上建索引,成功後再發送這個 Doc 到這個 Shard 的副本上建索引,等副本上建索引成功後才返回成功。

在這種架構中,索引數據全部位於 Shard 中,主 Shard 和副本 Shard 各存儲一份。當某個副本 Shard 或者主 Shard 丟失(比如機器宕機,網絡中斷等)時,需要將丟失的 Shard 在其他 Node 中恢復回來,這時候就需要從其他副本(Replica)全量拷貝這個 Shard 的所有數據到新 Node 上構造新 Shard。這個拷貝過程需要一段時間,這段時間內只能由剩餘主副本來承載流量,在恢復完成之前,整個系統會處於一個比較危險的狀態,直到 failover 結束。

這裏就體現了副本(Replica)存在的一個理由,避免數據丟失,提高數據可靠性。副本(Replica)存在的另一個理由是讀請求量很大的時候,一個 Node 無法承載所有流量,這個時候就需要一個副本來分流查詢壓力,目的就是擴展查詢能力。

角色部署方式

接下來再看看角色分工的兩種不同方式:

圖片

Elasticsearch 支持上述兩種方式:

  1. 混合部署(左圖)
  1. 分層部署(右圖):

上面介紹了 Elasticsearch 的部署層架構,不同的部署方式適合不同場景,需要根據自己的需求選擇適合的方式。

Elasticsearch 數據層架構

接下來我們看看當前 Elasticsearch 的數據層架構。

數據存儲

Elasticsearch 的 Index 和 meta,目前支持存儲在本地文件系統中,同時支持 niofs,mmap,simplefs,smb 等不同加載方式,性能最好的是直接將索引 LOCK 進內存的 MMap 方式。默認,Elasticsearch 會自動選擇加載方式,另外可以自己在配置文件中配置。這裏有幾個細節,具體可以看官方文檔。

索引和 meta 數據都存在本地,會帶來一個問題:當某一臺機器宕機或者磁盤損壞的時候,數據就丟失了。爲了解決這個問題,可以使用 Replica(副本)功能。

副本(Replica)

可以爲每一個 Index 設置一個配置項:副本(Replicda)數,如果設置副本數爲 2,那麼就會有 3 個 Shard,其中一個是 PrimaryShard,其餘兩個是 ReplicaShard,這三個 Shard 會被 Mater 儘量調度到不同機器,甚至機架上,這三個 Shard 中的數據一樣,提供同樣的服務能力。

副本(Replica)的目的有三個:

問題

上面說了一些優勢,這種架構同樣在一些場景下會有些問題。

Elasticsearch 採用的是基於本地文件系統,使用 Replica 保證數據可靠性的技術架構,這種架構一定程度上可以滿足大部分需求和場景,但是也存在一些遺憾:

上面介紹了 Elasticsearch 數據層的架構,以及副本策略帶來的優勢和不足,下面簡單介紹了幾種不同形式的分佈式數據系統架構。

分佈式系統

第一種:基於本地文件系統的分佈式系統

圖片

上圖中是一個基於本地磁盤存儲數據的分佈式系統。Index 一共有 3 個 Shard,每個 Shard 除了 Primary Shard 外,還有一個 Replica Shard。當 Node 3 機器宕機或磁盤損壞的時候,首先確認 P3 已經不可用,重新選舉 R3 位 Primary Shard,此 Shard 發生主備切換。然後重新找一臺機器 Node 7,在 Node7 上重新啓動 P3 的新 Replica。由於數據都會存在本地磁盤,此時需要將 Shard 3 的數據從 Node 6 上拷貝到 Node7 上。如果有 200G 數據,千兆網絡,拷貝完需要 1600 秒。如果沒有 replica,則這 1600 秒內這些 Shard 就不能服務。

爲了保證可靠性,就需要冗餘 Shard,會導致更多的物理資源消耗。

這種思想的另外一種表現形式是使用雙集羣,集羣級別做備份。

在這種架構中,如果你的數據是在其他存儲系統中生成的,比如 HDFS/HBase,那麼你還需要一個數據傳輸系統,將準備好的數據分發到相應的機器上。

這種架構中爲了保證可用性和可靠性,需要雙集羣或者 Replica 才能用於生產環境,優勢和副作用在上面介紹 Elasticsearch 的時候已經介紹過了,這裏就就不贅述了。

Elasticsearch 使用的就是這種架構方式。

第二種:基於分佈式文件系統的分佈式系統(共享存儲)

圖片

針對第一種架構中的問題,另一種思路是:存儲和計算分離。

第一種思路的問題根源是數據量大,拷貝數據耗時多,那麼有沒有辦法可以不拷貝數據?爲了實現這個目的,一種思路是底層存儲層使用共享存儲,每個 Shard 只需要連接到一個分佈式文件系統中的一個目錄 / 文件即可,Shard 中不含有數據,只含有計算部分。相當於每個 Node 中只負責計算部分,存儲部分放在底層的另一個分佈式文件系統中,比如 HDFS。

上圖中,Node 1 連接到第一個文件;Node 2 連接到第二個文件;Node3 連接到第三個文件。當 Node 3 機器宕機後,只需要在 Node 4 機器上新建一個空的 Shard,然後構造一個新連接,連接到底層分佈式文件系統的第三個文件即可,創建連接的速度是很快的,總耗時會非常短。

這種是一種典型的存儲和計算分離的架構,優勢有以下幾個方面:

這種架構同時也有一個不足:訪問分佈式文件系統的性能可能不及訪問本地文件系統。在上一代分佈式文件系統中,這是一個比較明顯的問題,但是目前使用了各種用戶態協議棧後,這個差距已經越來越小了。HBase 使用的就是這種架構方式。Solr 也支持這種形式的架構。

總結

上述兩種架構,各有優勢和不足,對於某些架構中的不足或缺陷,思路不同,解決的方案也大相徑庭,但是思路跨度越大,收益一般也越大。

上面只是介紹了分佈式數據(存儲 / 搜索 / 分析等等)系統在存儲層的兩種不同架構方式,希望能對大家有用。但是分佈式系統架構設計所涉及的內容廣,細節多,權衡點衆,如果大家對某些領域或者方面有興趣,也可以留言,後面再探討。

本文由 Readfog 進行 AMP 轉碼,版權歸原作者所有。
來源https://mp.weixin.qq.com/s/A-OahcqfKkgLt3xSk6Ukfw