/var/log/study

つまり雑記

ロードバランサー 入門準備

この記事は富士通クラウドテクノロジーズ Advent Calendar 2020の24日目の記事です。

23日目は id:foobaron さんの EVPN L2VPN All-Active MultihomingにおけるRoute Typeと経路迂回 でした。 データセンターのネットワーク運用者は要チェックです。

25日目は inasato さんの 「ESXi Arm Edition v1.1 で物理 NIC の追加してみた」 です。


アドベントカレンダー24日目の記事です。12/24といえばクリスマスイブです。どんなプレゼントがもらえるか?がワクワクする日ですね。インフラエンジニアならば誰しもがクリスマスにロードバランサーをプレゼントされるのを夢見たことがあるのではないかと思っています。

クリスマスとは関係ないですが、ロードバランサーを触る機会をいただくことが年々増えているため、一度ロードバランサーの入門前に知っておきたかった話 (もしくは一度知ってしまえばなるほどね。と思えるような話) をまとめておこうと思います。いろいろなことを書こうとは思いますが、LBに精通しているわけではないので抜け漏れはあると思います。

以下の文章でロードバランサーはLBと省略し、以下のようなことを記載します。

  • LBに期待されることの説明
  • LBの論理構成とその時に関わる用語や方式など
  • LBのよくある設定項目とその補足
  • LBを検証するに当たって用いると良い検証ツールの紹介
  • LBを知るに当たって参考となる資料

以下のようなことは本記事では記載しません。

  • 特定のLBが備える機能の詳細
  • LBを用いた負荷試験などの計画や実施方法
  • LBを運用する際に必要な考慮点
  • etc

LBに期待されること/LBで実現できること

基本的にはある1つの宛先に対する通信を受け取った際に、設定した複数の宛先に振り分けることがLBには期待されます。例えば1度目の192.0.2.1に対する通信を192.0.2.11に、2度目の192.0.2.1に対する通信を192.0.2.12に振り分ける、といった振る舞いを期待します。ユースケースとしては複数台用意した同一のwebアプリケーションサーバーに通信を振り分けること実現します。

1つの宛先を複数の宛先に振り分ける都合上、複数の宛先が宛先として機能するか?を確認し、宛先として機能しない場合は宛先としては見なさない様にすることもLBには期待されます。具体的な例を挙げると、LBから一定の間隔で振り分け先のIPに対してICMPでの通信を試みて、複数回の返信がなければ振り分け先のサーバーから除外する様な振る舞いを期待します。ICMPは具体例の一つで、試みる通信のプロトコルや試みる頻度が選択可能であることも期待されます。通信の振り分け先が全て不能の状態だと判定した際にはLBがエラーのページをレスポンスすることも期待されます。

また、LBはクライアントとコンテンツをレスポンスするサーバーの中間に位置する都合、複数の振り分け先で処理するよりも中間のLBで処理してしまった方が良いことを処理することも求められます。よく挙げられる例としては、SSL/TLSの通信の終端や、特定の通信を許可/拒否するフィルタリングですが、解釈するプロトコルがより高レベルなものだと、認証認可のための処理を挟むことができたりします。

最後に、LBは、ある宛先に対する通信を1度集約し、分散させる装置である都合上、LB自身に可用性が期待されます。具体的には, 2台以上の同様なLBでActive/Stanbyの構成や、Active/Activeの構成が取れることを期待されます。また1台のLBに障害が発生した際にも、既存の通信に与える影響を最小に通信の処理を継続できることが求められます。

LBとネットワーク構成など

ここではLBのネットワーク構成などについて言及しようと思います。 物理的な話や論理的な話での分類というよりは、対比しやすい話を記載していきます。

アイコンと図の説明

以降いくつかアイコンを用いた図を使いますが、以下のようなイメージで使い分けています。また黒い線はネットワーク的な繋がりを、オレンジ色の線は通信の経路を示すつもりで利用しています。

イメージをつかむ足がかりになることを目的としているので、正確な構成図は示しません。

また特にロードバランサーのアイコンは後述するLB装置/バーチャルサーバー/LBインスタンスとしてのアイコンを特に使い分けていません。話の文脈的にLB装置であるか、バーチャルサーバーであるか、LBインスタンスであるか?を識別するのが重要なときだけどのような役割でLBアイコンを使っているか記載します。

f:id:yaaamaaaguuu:20201224041936p:plain

バーチャルサーバー

LBと一口に言っても、物理的なハードウェアを利用して実現する方法や、仮想サーバー上のOSにソフトウェアをインストールして実現する方法などあります。

物理ハードウェアや仮想サーバーなど複数のLBのための装置を1セットのLBとみなした時、更にそのLBの中で複数のロードバランスの設定を持つことができるケースが多いです。LB装置内部に仮想的なサーバーを持つようなイメージでバーチャルサーバーと読んでいるようです。ここではバーチャルサーバーと書きましたが、この呼称はLB製品によってまちまちだと思います。

下記の図でLBのアイコンは、実際にパケットを処理しているプロセス的な何かだとイメージしてください。良い言葉が無いのでこの文章ではLBインスタンスと呼びます。

LB装置とバーチャルサーバーの設定と、LBインスタンスなどの組み合わせにより無限に考え方があると思うのでコレはあくまで一例です。

例えば、Active/Stanby構成のうち、片方のバーチャルサーバーの通信を処理するLBインスタンスのActive/Stanbyを入れ替えるとLB装置としてはActive/Active に見えたりすると思います。 (実際に通信を賄うのはどちらかになるので、バーチャルサーバーから見たらActive/Stanbyは変わらないですが。)

またLB装置が複数のケースでもそうで、バーチャルサーバーの設定の適用範囲や、その適用範囲のうちどのように通信を処理するLBインスタンスが稼働して通信をさばいたりは様々な組み合わせがあります。モノによって組める構成は異なると思うので要確認です。

f:id:yaaamaaaguuu:20201224093139p:plain

VIP

バーチャルサーバーは通信を受け付けるIPを設定する必要があります。その通信を待ち受けるIPをVIP (ビップもしくはブイアイピイ)と呼びます。バーチャルサーバーのIP で Virtual IPとのことです。

2台構成, 複数構成

前述したようにLBには可用性が求められます。2台のLB装置でActive/Stanbyの構成を作り、Activeが障害を起こすとStanbyに切り替える構成をよく聞きます。またソフトウェアで実現するロードバランサーでは3台以上のLB装置を連携させる方式も聞きます。

特にソフトウェアベースのLBで3台以上を連携させるときに見かける方式としては、代表のノードが一度通信を受取、L2の宛先を書き換えて他のLB装置に転送する方式と、上位のルーターとBGPで連携し上位ルータの段階で複数のLB装置に通信を分散させる多段なロードバランサーを構成する方式を見かけます。

以下の図では振り分け先サーバーを省略していますが、オレンジ色の先が届いているActiveと記載されているLBから振り分け先に通信を転送することになります。

f:id:yaaamaaaguuu:20201224042723p:plain

1arm, 2arm/インライン

続いてイメージしやすい話を記載すると、1arm, 2armインラインがあると思います。 1armは通信を受け付けたNICから振り分け先サーバーに通信を転送する構成で、2arm/インラインは通信を受け付けたNICとは異なるNICから振り分け先に通信を転送する構成になります。

f:id:yaaamaaaguuu:20201224042945p:plain

ロードバランサーを介した通信の送信元IP

クライアントとクライアントからのリクエストを処理する間にロードバランサーが存在することになります。クライアントからロードバランサーがVIPで通信を受け付けた際に、送信元IPアドレスロードバランサーが書き換えずに振り分け先にパケットを転送するのが透過IP(P透過, 透過モード)、 送信元IPアドレスロードバランサーが設定されたIPに書き換えるのがSNAT (透過IPと対比して、非透過と呼ばれることもあるらしい) です。

また送信元IPを書き換えてしまうと、振り分け先サーバーでは本来の送信元が不明になります。そのための対策としてHTTPの通信をロードバランスする際にX-Forwarded-Forヘッダーにもともとの送信元IPを記載する機能や、HTTPも含めその他のプロトコルの際にも送信元がわかるようにProxy Protocolに対応する機能があったりします。

フローティングIP

Active機が故障し、Stanby機がActive機に昇格するような際に、Active側で待ち受けていたIPをStanby側に引き継ぐ必要があります。所有者が変わる必要があるさまを指してFloating IP と読んでいるみたいです。

個人的にはStackoverflowのこの解答 を読んでわかった気分になりました。

ロードバランサーのよくある設定項目/確認ポイント

複数のロードバランサー製品を見て共通で備わっている機能には以下のような項目があります。 この項目と、前述のネットワーク構成の設定を組み合わせてロードバランサーを実現することになります。

具体的な要件が決まっている設定値は、要件が満たされているか?を確認すると良いと思いますが、そうでない値はどのような機能があるかを眺めながら動作確認することになると思います。

  • 振り分け可能なプロトコル
    • どのようなプロトコルが振り分け可能か?を確認すると良いです。
    • また振り分けたいプロトコルによって(特にL4とL7を境界として)できることが異なるので把握すると良いです。
        • HTTPSをLBで受付SSL/TLSを終端し、振り分け先サーバーにはHTTPで通信を流すなど
        • HTTPを振り分ける際にX-Forwareded-For ヘッダーを挿入したり。
  • 振り分け先選定
    • どの様な振り分け先選定方法があるのか?を確認すると良いです。
    • round robin や least connection などがありますが、正確なことは利用するLBのドキュメントを読むのが良いです。
  • 振り分け先固定
    • HTTP通信のセッションの保持の都合などで、1度アクセスしたサーバーにしばらく接続され続けるのが好ましいケースがあります。
    • どのように振り分け先を固定することが可能かを把握すると良いと思います。
    • また振り分けの固定がどれだけ持続するか?も確認すると良いと思います。
  • ヘルスチェック
    • ヘルスチェックの試行方法
      • どのようなプロトコルでヘルスチェック可能か?
      • ヘルスチェックの試行間隔はどれくらいか?
    • ヘルスチェックの失敗判定の条件
      • 1つの振り分け先が振り分け不可と判定する条件は何か?
      • 1回の試行は何を満たすと失敗と判定されるか?
    • ヘルスチェック失敗からの復帰条件
      • 「ヘルスチェックが3回成功したら復帰と見なす」などの条件を見ると良いと思います。
  • エラーページについて
    • どの様にエラーページを設定可能か?
      • リダイレクト
      • 固定ページの表示
      • その他
  • フェイルオーバー時の挙動
    • 求める要件によっても変わってくるので一例となります。
    • ロードバランサー自体がどの様に障害を検知し、フェイルオーバーするか?
      • 確認すべきポイントは構成に依存するので詳細は追わないです
    • 障害検知までの時間, 障害検知から通信を処理する筐体の切り替わりまでの時間
      • 障害の検知は早ければ早い方が良いですが、誤検知しない程度が求められます
    • 既存の通信に対する影響
      • 障害を検知したLBを介していた通信が、LBの切り替わり後も問題なく通信可能か

ロードバランサーを検証するに当たって用いると便利な検証ツールの紹介

検証をする際に利用すると便利なツールを雑多にいくつか紹介しておきます。これらのツールを用いて、前述の設定項目/機能が意図通り動作しているか?を確認していくことになると思います。

ここで上げるツールは基本的にLinuxで使えるものを挙げます。

  • netcat
    • The GNU Netcat -- Official homepage
    • ncと呼ばれたりもします。
    • netcat1つでTCP/UDPの擬似的なクライアントとしても、擬似的なサーバーとしても活用することができます。
    • 例えば、shellとうまいこと組み合わせる事で擬似的なwebサーバーとしても動かすことが可能です。
  • curl
    • curl
    • 特に自分から説明することがないくらいには有名なツールだと思いますが、一応
  • nmap
  • tcpdump
  • Wireshark
  • NGINXとngx_http_perl_module
    • Module ngx_http_perl_module
    • webサーバーと、perlをもちいて動的なコンテンツを返すモジュールです。
    • ngx_http_perl_moduleを推す理由は、多くの場合NGINXをインストールすると利用可能だからです。
      • nginxと適当な言語のアプリケーションサーバーを組み合わせて… という様なことが得意であればそちらを使う方が良いと思います。
    • 例えば、以下の様なことを実現したいケースで便利です。
      • 振り分け先サーバーが認識した、送信元IPをレスポンスに記載する
      • 振り分け先のサーバーのホスト名をレスポンスに記載する
      • 振り分け先サーバーに届いたHTTP通信のX-Forwarded-Forのヘッダーの中身をレスポンスに記載する
  • Fabric
    • Welcome to Fabric! — Fabric documentation
    • 複数のサーバーに対して、コマンドを実行することができるpython製のツールです。
    • pythonのコードの中に、実行したいコマンドを記載する形式になります。
    • 手軽に複数の振り分け先サーバーのセットアップ/設定変更する際に便利です。
    • 使い慣れていればAnsibleなどでも良いと思います。
  • Locust
    • Locust - A modern load testing framework
    • 適当なHTTP/HTTPSリクエストを多数飛ばしてみるのに便利なツールです。
    • pythonでシナリオを書いてHTTPのリクエストを飛ばす順序などを設定できます。
    • WebのUIもあり便利ですが、CLIで完結することも良いポイントだと思います。
      • locustのcliから生成するリクエストするクライアントの数の上限や、クライアントの増やし方などを設定することができます。
    • 複数サーバー上で複数のlocustを稼働させ、大量の通信を飛ばすのも比較的容易です。
      • locustの1プロセスは1cpuしか使わないような作りになっていたと思うので、小さい複数のサーバーでlocustを動かすのが良いと思います。
  • Apache JMeter
    • Apache JMeter - Apache JMeter™
    • こちらもHTTP/HTTPSのリクエストを多数飛ばすツールとなります。
    • 先人たちがJMeterでパフォーマンス計測した結果が残っていたりするケースがあると思うので、使えて損がないと思います。

本記事の参考文献 もしくはLBを学習するに辺り参考になった文献

自分がLBを学ぶにあたっては、以下の資料が大変参考になりました。

書籍

  • サーバ負荷分散入門
    • 前半は負荷分散技術に関して書かれています。
    • 後半はF5社のBIG-IPのLTMの仮想アプライアンスを利用したものとなっています。
      • 書籍で扱っている内容はv11系列で、最新版はv16系のようです。
      • 学習時に触っただけなのでBIG-IPのLTMに関しては全く詳しくないのでv11とv16系でどれだけ違うのか?不明です。
      • 自分は後半を流し読みしてしまったので、BIG-IP v16系 でも書籍通り検証できるか?も不明です。

Web

まとめ

ロードバランサーの初歩的な話をまとめて記載しました。将来的に誰かの役に立てば幸いです。


この記事の図は https://app.diagrams.net/ニフクラ アイコン&シンボル を利用して記載しました。

この記事は富士通クラウドテクノロジーズ Advent Calendar 2020の24日目の記事です。

23日目は id:foobaron さんの EVPN L2VPN All-Active MultihomingにおけるRoute Typeと経路迂回 でした。

25日目は inasato さんの 「ESXi Arm Edition v1.1 で物理 NIC の追加してみた」 です。 Raspberry Piで実現できるESXi Armの欠点を克服しそうなネタなので楽しみですね。