SRVレコードサービス検出とDocker APIサービス検出のネイティブ実装を備えた新しいL4ロードバランサー

それがすべて始まった方法



マイクロサービスを使用する過程で、自動スケーリング中のディスカバリーのサービス、余分なノードの崩壊に関する問題に繰り返し遭遇しました。







存在する、または現時点で存在するほとんどすべての解決策が試されましたが、いつものように-動的な環境(1時間あたり同じ種類のコンテナの数十の停止/開始)に完全に落ちるものはありませんでした。 最も近いソリューションはNGINX + Consul + Consulテンプレートでしたが、butく、再起動が必要であり、Consul以外の外部helchecksを使用できませんでした。







一般的に、いつものように-あなたの決定を書くことが決定されました。 議論の中で、私たちにとって最も重要であり、一般の人々にとって興味深いものであると思われる、実装に適したものが数十個選ばれました。







最初の反復の組み込み機能



バランスの種類:



イファッシュ

Leastconn

ラウンドロビン

重さ







ディスカバリー(各フロントエンドのバックエンドプールの定義):



静的は、構成内のサーバーの単なるリストです。

Docker-ラベルおよびコンテナーの内部ポートによってフィルター処理されたDocker / Swarm APIドッカーリクエスト。

Exec-外部スクリプトの起動を開始し、stdoutから読み取り、定期的に(ハードに登録されている間に)解析します。

JSON-httpリクエストを介してURLをリクエストし、それをパターンに解析します(マルチレベルJSONをサポートします)。

プレーンテキスト-httpリクエストを介してURLをリクエストし、設定で指定された正規表現に従ってURLを解析します。

SRV-特定のDNS SRVレコードをサービス名で要求します。







ヘルシェキ



当初、同じhaproxyボリュームにhelchecksを実装するために単純に引き出さないことが明らかだったため、少し血を流して2種類のhelchecksを作成することにしました。







Ping-単純なTCP ping。

Exec-パラメータを渡して任意のバイナリを起動し、stdoutから出力を読み取ります。







使用例



SRVディスカバリー



たとえば、Consulに登録する任意のサービスがあります。 Consul dnsを使用して、サーバープールを決定します。







画像







この例では、バランシングのタイプを「srv」と定義しました。DNSサーバーとそのポートも定義されており、ディスカバリーサービスへの要求が送信されます。 サーバーのリストを更新する頻度と重要な変数(DNSサーバーが応答しなかった場合のポリシー)が決定されました。 環境の一貫性を最大にするには、failpolicy = "setempty"に設定します。 この場合、DNSからの応答がない場合、サーバーバックエンドのプール全体がリセットされ、着信接続がドロップされます。 それ以外の場合は、failpolicy = "keeplast"を使用する必要があり、バランサーはDNS接続が失敗する前に来た最新のデータを使用します。







toml [servers.sample2] bind = "localhost:3001" protocol = "tcp" balance = "weight" [servers.sample2.discovery] failpolicy = "keeplast" kind = "srv" srv_lookup_server = "66.66.66.66:8600" # dns server and port srv_lookup_pattern = "api.service.ireland.consul." # SRV service pattern [servers.sample2.healthcheck] fails = 1 passes = 1 interval = "2s" kind = "ping" timeout = "500ms"
      
      





Docker / Swarm Balance。



実際、Docker / Docker SwarmのAPIと構成方法に違いはありません。 DockerホストおよびDocker Swarmクラスターと同等に作業できます。 一例でそれらを使用することを検討してください。







画像







次に、より一般的な例として、Docker Swarmを使用して特定のサービスのバランスを取ります。 以下のすべては、個別のDockerホストで機能します。 この例では、ディスカバリーのタイプを「docker」として定義し、ベースドッカーURL、ラベル、およびドッカーコンテナーの内部ポート(コンテナー自体のネットワーク側から)を定義します。これにより、バランサーがサーバーバックエンドプールの形成元を選択します。







この例では、より高度なタイプのhelchecks、つまりexec helchecksを使用します。 チェックを開始するためのパラメーターに加えて、スクリプトの実行時間もあります。 「レイド」が発生しないように、起動間の時間はスクリプトの実行時間よりも長くする必要があります。 このhelcheckを起動するコマンドは、/ path / to / script [ip] [port]として形成されます。 スクリプトを作成した後、正と負の予想結果と比較される文字列を標準出力に出力する必要があります。







 [servers.sample3] bind = "localhost:3002" protocol = "tcp" balance = "weight" [servers.sample3.discovery] interval = "10s" timeout = "2s" kind = "docker" docker_endpoint = "http://localhost:2377" # Docker / Swarm API docker_container_label = "api=true" # label to filter containers docker_container_private_port = 80 # gobetween will take public container port for this private port [servers.sample3.healthcheck] kind = "exec" interval = "2s" exec_command = "/etc/gobetween/checks/exec_healthcheck.sh" exec_expected_positive_output = "1" exec_expected_negative_output = "0" exec_timeout_duration = "1s"
      
      





将来の記事では、他のタイプのディスカバリーのより複雑な使用の例をいくつか紹介する予定です。 Windowsでの構成とインストールの詳細についても説明します。










All Articles