Serfソース分析-概要

2383 ワード

Serfとは何ですか.
Serfはhashicorpオープンソースの非中心化メンバー管理、失敗検出、サービス編成ツールであり、軽量レベル、高可用性、パーティションフォールトトレランスの特徴を有する.Serf下位層はgossipプロトコルを採用し,クラスタ内でメッセージをブロードキャストすることでクラスタ内のノードダウンラインの自動感知を実現した.最終的な整合性はgossipプロトコルによって達成されるので,SerfはAPシステムである.Serfは、ロードイコライザ、Memcached、またはRedisクラスタ管理、DNSレコード更新などのシーンに適用することができる.
Serfはどのように動作しますか?
Serfはgossipプロトコルに基づいて構築され、「SWIM:Scalable Weakly-consistent Information-style Process Group Membership Protocol」論文のアルゴリズムを実現し、クラスタ内の各ノードは1つのメンバーリストを維持し、失効検出器モジュールによってノードがダウンタイムしているかどうかを検出し、伝送コンポーネントはノードメンバーリストを交換合併し、クラスタのいくつかの状態を更新する.
Serf伝播コンポーネント
伝播コンポーネントでは、ノードはメンテナンスされたメンバーリストをクラスタ内のいくつかのノードにランダムに送信し、情報交換を行う.一般的には、Anti-entropyとRumor mongeringの2つの交換モードがあります.Anti-entropyはノードの全量情報を交換し,Rumor mongeringはノードの増分情報を交換する.各モードについて、具体的には、Push、PullまたはPush-Pull混合方式を採用することができる.Push方式は、他のノードに新しい情報を積極的に提供します.Pull方式はランダムにいくつかのノードを選択し、自分の情報をプッシュする必要がある.Push-Pullハイブリッド方式ではPushとPullを組み合わせて情報を双方向に交換する必要がある.SerfはAnti-entropyモードを採用し,情報交換にPush-Pullブレンド方式を用いた.
Serf実効検出器
失効検出器は,メンバーリストをポーリングし,心拍情報を定期的に送信することによってノード状態を検出する.心拍情報は様々な通信方式で送信され、まずUDPパケットが指向的に送信され、タイムアウト時間内に確認応答が受信されなければ、ランダムにいくつかのノードが選択され、中継ノードに間接心拍情報を送信することによって、中継ノードにノード状態の決定を依頼する.中継ノードがまだ返信を受信していない場合、ノードは疑似実効ノードとしてマークされ、決定されたしきい値範囲内で返信情報が受信されていない場合、ノードは最終的に実効ノードとしてマークされます.
「Vivaldi:A Decentralized Network Coordinate System」論文のアルゴリズムを実現した、Serfで採用されているgossipプロトコルには、ネットワーク診断機能が組み込まれている.ノード間RTT時間は、クラスタ内のノードの多次元座標を維持することによって計算される.
Serfクラスタ構築
Serfはコマンドライン要求の受信をサポートし,ノード追加,ユーザクエリー,イベント処理を実現する.2つのノードを構築するクラスタを例に,Serfがコマンドライン要求をどのように処理するかを説明する.
まず、公式サイトからバイナリ圧縮パッケージをダウンロードし、解凍した後、バイナリ実行可能ファイルにします.
agentコマンドを実行して、クラスタ固有の名前foo、gossipポートバインドアドレス127.0.0.1:5000、クラスタ間rpc通信ポートバインド127.0.0.1:7373を持つSerfノード1を起動します.
serf agent -node=foo -bind=127.0.0.1:5000 -rpc-addr=127.0.0.1:7373

同じ形式のコマンドでSerfノード2を起動します.
serf agent -node=bar -bind=127.0.0.1:5001 -rpc-addr=127.0.0.1:7374

このときすでに2つのノードが起動しているが,この2つのノードは互いに存在することを知らない,すなわちクラスタが形成されていない.ノードが互いに認識できるようにするには、既知のクラスタに手動でノードを追加する必要があります.これは、Serfのjoinコマンドを実行する必要があります.
serf join 127.0.0.1:5001

このコマンドはfooノードに,ノードbarが存在するクラスタに加わることを教える.クエリーコマンドmembersを使用すると、クラスタノードのステータスが表示されます.
$ serf members
foo    127.0.0.1:5000    alive
bar    127.0.0.1:5001    alive

クラスタには既にalive状態のノードが2つ存在し,このテストで使用したSerfクラスタの構築に成功していることがわかる.