Skip to content

Instantly share code, notes, and snippets.

@261shimizu
Last active February 4, 2019 11:12
Show Gist options
  • Star 3 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save 261shimizu/f16e314ec6b93e0b5d9d4304ac57c464 to your computer and use it in GitHub Desktop.
Save 261shimizu/f16e314ec6b93e0b5d9d4304ac57c464 to your computer and use it in GitHub Desktop.
クラスタリングとか、ロードバランサとか、iSCSIとか

クラスタリング概要

以前のまとめは、深いとこまでツッコミ過ぎているのと、理解できずに書いているので上手くまとまっていない。
この機会にまとめ直す。
引用部分は内容が細かくなってしまった部分なのでざっと読む場合は飛ばして良し。

大雑把な分類


クラスタリングと言った際、本質は「房」であり、複数のサーバを1台に見せることであるが、
実務的にはHAクラスタが重要なんじゃなかろうか(というかそれ以外知らない。。。)

HAクラスタリングは、厳密には負荷分散もフェールオーバーも含んでいる?気がする。
(なんとなくHAクラスタ:フェールオーバと負荷分散クラスタを分けて記述しているものもある気がする。)
HA=高可用性、であるので、根本はサービスを止めない為に、

  1. なるべく壊れない様にする
  2. 壊れてもサービスを継続する

の2本柱になり、それぞれに対応するのが、

  1. 負荷分散(ロードバランサ) → LSV等
  2. フェールオーバー → keepalived , pacemaker

となる。

フェールオーバークラスタ概要


フェールオーバークラスタとは、同じ構成のサーバをAct-Stanby方式で用意し(2台とは限らない)、
Act(マスター)機が壊れた際にそれを検知してStanby(スレーブ)機にサービス提供させる仕組みを言う。

クライアント-サーバ構成を考えた時、クライアントはAct機が壊れても、それを意識せずにサービスを教授出来る。
これは仮想的なIPアドレスをAct機に割り当てていて、Act機の故障をクラスタが検知すると、
Stanby機に仮想IPを割り当てる(フェールオーバする)ことで実現できる。

この時の仮想IPを 「リソース」 と呼び、リソースの割り当て及び管理がフェールオーバクラスタの基本。
リソースは仮想IPの他にも、サービスによってWebサービス(Apache,Nginx等)や、AP、DB、ディスク等が考えられる。

故障の検知には、 インターコネクト という専用ネットワークを使用する。
これはサービス提供用のネットワークとは別に、サーバ間での通信に使用されるもので、
このサーバ間の通信を持ってAct機の状態を監視している。

※仮想IPについては以前のまとめを参照のこと。
※仮想IPだけでは不足することがある。仮想MACアドレスを割り当てる方法もあるらしい。
(これによってTCP/IPのレイヤ以外でもクラスタが使える。以前のまとめを参照)
※単にマスターとスレーブで別れていれば良いが、あるサービスはAサーバをマスターに、
別のサービスはBサーバをスレーブに、とした場合はもっと複雑になる。

負荷分散概要


負荷分散や、ロードバランサと呼ばれるものは基本的にクライアントとサーバの間に置かれる。
主な役割はその名の通り、負荷を分散させることで、サービスを壊れにくくさせる事。

例えば、同じ構成のサーバが2台あった時、1台だけで処理を行っていると、アクセスが集中した際に壊れやすくなる。
これを解決するために、クライアントからの要求をロードバランサが受け、どちらのサーバに処理をさせるか決める。
以上が負荷分散の基本的な仕事。

上記の様に、クライアントからアクセスする際にはロードバランサが宛先になるが、
サーバからのレスポンスは、ロードバランサを介さないこともある。

基本的にはロードバランサは死活監視(サーバが生きているかどうかを監視する)機能を持たない。
その為、ロードバランサとフェールオーバクラスタをセットで使うことが多い。

上記のフェールオーバクラスタの説明では、サービス提供サーバをフェールオーバしているが、
ロードバランサ・フェールオーバクラスタをセットで使う場合、
ロードバランサ自体を冗長化し、マスターのロードバランサが壊れた場合に備えることが常。

つまり、ロードバランサのサービス自体をリソースとして管理するということ。

使用されるソフトウェア


ロードバランサは専用の筐体がある。
しかし高価なため、ロードバランサ機能を提供するソフトウェアをサーバに導入する場合ことも多い。

冒頭でも書いたように、

  • フェールオーバクラスタ → (keepalived,) pacemaker
  • 負荷分散 → Linux Virtual Server(LVS), keepalived

がよく使用されるらしい。

  • pacemaker

    pacemakerは、corosync又はheartbeatとセットで使用する。
    pacemakerが リソースの監視・制御 を行うのに対し、
    corosync/heartbeatは 通信層制御=ノードの死活監視 を行うらしい。
    つまり、pacemaker+corosync/pacemaker+heartbeatとして冗長化 機能 が完遂する。
    現在は pacemaker+corosync が推奨されている。

    pacemakerについては訳わからんというのが正直なところで、
    歴史的な位置づけではHeartbeatの後継(機能の一部を切り分けてpacemakerとしたらしい)。
    このため、pacemakerとHeartbeat又はCorosyncを組み合わせて使用するらしい。

    機能 としては以上だが、 管理コマンドとして、 pcscrm が存在する。
    ここが一番意味不明な部分で、pacemakerの公式的なところでは、推奨が crm となっているのに、
    RHEL/CentOS7としては推奨が pcs となっている。訳わからん。

    pcsを使用するなら、 yum install pcs fence-agents-allとすれば依存関係で必要な物は全て揃うらしい。
    crmなら、tarファイルダウンロードからのローカルインストールかな?
    crmはエクセルファイルとかをインポートして設定ファイルにするらしい。

  • LVS

    予め設定した条件を元にクライアントからのリクエストをサーバに流すソフトウェア。
    LVSはRedhatやCentOSではデフォルトでカーネルに 機能 が組み込まれている模様。
    この機能を使用する為、設定や管理を行うコマンドが ipvsadm コマンド。
    コマンドはyum等でインストール可能。

  • keepalived

    役割は、 ロードバランサ機能及びHAクラスタ機能の実現
    つまり、 LVSで負荷分散しているサーバの死活監視と仮想IPを用いたLVS自身の冗長化 を行う。
    色々あるが、LVSとVRRPを管理するためのツールと認識すればおk

    keepalivedでも冗長化構成のフェールオーバクラスタを組むことは出来るらしい。
    (ただリソースは仮想IPのみ?)
    しかし、LVS+keeepalivedとして語られる事が多く、そもそもkeepalivedはLVSをラッピングして管理しやすくしてくれるもの
    という記述もある。LVS前提で開発されてるっぽいし。
    実際にLVSの設定を動的に変更する機能もあるみたい。
    VRRPという仕組みを実装していて、サーバ間でVRRPを行い死活監視をする。
    本来はVRRPはルータ冗長化の仕組みだが、サーバ冗長化に応用可能。

    どちらかと言えばLVSがロードバランサの機能寄りな分、keepalivedが冗長化寄りな気がするだけかもしれないが、
    そうやって理解してもあんまり問題にならないような気がする。

フェールオーバクラスタ詳細

概要


ここでは、フェールオーバクラスタの詳細について触れる。
分類は以下の通り。

  • フェイルオーバークラスタ
    • 共有ディスクタイプ
    • データミラータイプ

フェイルオーバークラスタ


フェイルオーバークラスタは、壊れたときの損害をできる限り小さくするシステム。システムダウンタイムを減らすことが目的。
クラスタ化されていないシステムでは、アプリケーションを他のサーバで再起動させると、クライアントは異なるIPアドレスに再接続しなければならない。
しかし、多くのクラスタシステムでは、業務単位に仮想IPアドレス(※)を割り当てている。
このため、クライアントは業務を行っているサーバが現用系か待機系かを意識する必要はなく、まるで同じサーバに接続しているように業務を継続できる。

※仮想IPとは、通常のIPとは別のIPを動的に割り当てるもの。 Linuxには1つのNICに通常のIPアドレスの他に、エイリアスIPアドレスという、別のIPを設定する機能があり、この機能を利用している。
つまり、クラスタリングソフトが仮想IPを確保して、死活監視して、割り当てる。
実は、仮想IPだけでなく、MACアドレス毎引き継ぐ方式もある。
これの利点は、TCP/IP以外のプロトコルでの通信でも引き継げる点にある。

  • 共有ディスクタイプ

クラスタシステムでは、サーバ間でデータを引き継ぐ必要がある。
このデータを共有ディスク上に置き、データを複数のサーバで利用する形態を共有ディスクタイプという。

データを引き継ぐ為には、ファイルシステムの整合性をチェックしなければならない。
このチェックにはfsckやchkdskを使用するので、ジャーナリングファイルシステムなどでフェイルオーバー時間を短縮する

更に、業務アプリケーションは、引き継いだデータの論理チェックをする必要がある。
例えば、データベースならロールバックやロールフォワードの処理が必要。
これらによって、クライアントは未コミットのSQLを実行するだけで業務を継続できる。

復旧後は、待機系として上がるので、(双方向スタンバイ※等で)必要なら応じてフェイルバックする。

※業務が複数で、かつ負荷分散のために業務毎に処理を行うサーバが異なる場合、
(業務AについてはサーバAが現用系、サーバBが待機系だけど、業務BについてはサーバAが待機系、サーバBが現用系というような状況)双方向スタンバイという。
つまり、例えば片方が障害発生すると、全ての業務の現用系がもう片方になってしまい、高負荷となる。

  • データミラータイプ

共有ディスクは、複数サーバで同じディスクを共有していたが、データミラータイプでは、共有ディスクを持たない。
クラスタを構成するサーバすべて、自分の持っているディスクに対して読み書きをする。
各サーバの各ディスクをすべてミラーリングするので、内容がばらつかない。

データミラータイプはこの特徴(サーバ間でデータをミラーする)のため、大量のデータを必要とする大規模システムには向かない。

詳細実現方法は以下の通り。
アプリケーションからのwrite要求が発生すると、データミラーエンジンはローカルディスクにデータを書き込むと同時に、インターコネクト(※)を通して、待機系サーバにもwrite要求を振る。
待機系のデータミラーエンジン(※)は、受け取ったデータを待機系のローカルディスクに書き込むことで、現用系と待機系のデータを同期する。
アプリケーションからのread要求に対しては、単に現用系のディスクから読み出すだけ。
現用系のディスクに障害があった場合、データミラーエンジンは障害発生ディスクへの書き込みは行わず、インターコネクト経由で待機系ディスクのみへ読み書きを行う。

※インターコネクトとは、サーバ間をつなぐネットワークのことで、クラスタシステムでは死活監視のために必要。
データミラータイプでは、死活監視に加えてデータの転送に利用する。
※データミラーエンジンは、要求の窓口みたいなもの。各サーバにある。

データミラータイプの応用例としては、スナップショットバックアップの利用がある。
通常、スナップショットバックアップには時間がかかるが、データミラータイプの場合、待機系をクラスタから切り離せば、その待機系がまるまるバックアップとなる。

共有ディスクタイプの問題点


共有ディスクタイプは、マウントすることによって共有ディスクを使用可能にする。
しかし、複数サーバが同時にマウントされると、データが破壊されかねないので、ディスクの排他制御を行っている。

どういう時に同時マウントが起こるかというと、ネットワークパーティション問題というものがある。
サーバ間をつなぐインターコネクトが切断されたとき、各サーバは、もう一方との死活監視ができず、もう一方に障害が発生したと認識する。
インターコネクトが切断されているので、双方でこの状態になるため、自分が処理を引き継ごうと、それぞれで共有ディスクをマウントしてしまう。
このようにして同時マウントが発生する。

この同時マウントを回避するために排他制御を行う
排他制御を実現するためにSCSIコマンドのRESERVEを利用するクラスタシステムがある。
共有ディスクを使用するサーバは共有ディスクをRESERVE状態にすると同時に、他のサーバからのRESERVE要求があると、
RESERVATION_CONFLICTを返すことで排他制御を実現する。
共有ディスク使用中のサーバがダウンした場合、共有ディスクを引き継ぐサーバ側でRESETコマンドを発行し、RESERVE状態を強制的に開放(RELEASE)した後、対象をRESERVEする。

ネットワークパーティション問題が発生した場合、タイミングによって、RESERVEを獲得したサーバに優先権が与えられる。

参考


@IT Linuxクラスタリングへの招待(1)~(4)

ロードバランサ詳細

ロードバランサの詳細。

概要


負荷分散クラスタの分類は以下。

  • 負荷分散クラスタ
    • ロードバランスクラスタ
    • 並列データベースクラスタ

フェールオーバと違い、システムダウンタイムの現象が目的ではなく、負荷を軽減することでサーバがダウンする確率を下げ、可用性向上を狙うシステムのこと
ロードバランスクラスタと並列データベースクラスタがある。

それぞれの概要


  • ロードバランスクラスタ

    ロードバランサを使うことで、急激なアクセスの増加に対応できたり、サーバを止めずにサーバの更新やメンテナンスを行うことができる。
    例えばECサイトなどでサーバを止めてしまうと、せっかくのアクセスを逃すことになり、もったいない。

    アクセスをロードバランサで受けて、ロードバランサがうまい具合に負荷分散するようにサーバに要求をふる。(要求の中継)
    これによって、サーバが1つダウンしても、他のサーバがリクエストを処理し、さらに速いレスポンスを実現できる。

    なので、クライアントからの宛先IPはロードバランサのIPになる。ここが仮想IPと異なる(仮想IPはサーバに割り当てられる。)
    しかし、マルチポイント方式だと、各ノードが同じIPを持つ方式になり、ロードバランサの専用装置で受けるわけではない。各サーバが受け付ける。
    分散方式の詳細は後述する(方式はいくつかある)。

  • 並列データベースクラスタ

    並列データベースクラスタは、複数のデータベースサーバで処理の分散と可用性の向上を狙うクラスタシステムをいう。
    並列データベースエンジンは、サーバ間通信によるデータベースの管理と各サーバの状態管理を行うことで、処理の分散と可用性の向上を行っている。

ロードバランサ詳細


ロードバランスクラスタの負荷分散の実現方法は2つある。

  1. マルチポイント方式
  2. コーディネータ方式

更に、分散アルゴリズムもいくつかある。

  1. ラウンドロビン
  2. 最小コネクション
  3. 最速応答
  4. CPU負荷分散

更に更に、LVSでは、リクエストのサーバへの転送方式も幾つかある。

  1. NAT
  2. ダイレクトルーティング
  3. トンネリング

更にさらに、セッション維持(Sticky)方法もいくつかある

  • ソースIPによるSticky
  • http CookieによるSticky
  • SSL Session IDによるSticky
  • URLによるSticky
  • 携帯電話へのSticky

負荷分散実現方法


  • マルチポイント方式

分散ノードであるサーバが同じ仮想IPを持っている。要求はすべてのノードが受け付ける。
各ノード間ではネゴシエーションを行っていて、次にどのノードが処理するか決める。

ノード間のネゴシエーションのオーバーヘッドが大きくなるが、クライアントへダイレクトにレスポンスを返すことによってスループットを向上させている。

メリットはコーディネータ方式のように専用装置を必要とせず、既存のサーバに組み込むことで負荷分散環境を構築できる。

  • コーディネータ方式

一般的に負荷分散装置(専用ハードウェアあるいはソフトウェア実装)で実現している方法・
クライアントからのすべての要求をいったん装置で受け、配下のノードに対して分散させる。

負荷分散アルゴリズム


  • ラウンドロビン
    配下の分散ノードに対して、要求を順番に割り振る。

  • 最小コネクション
    コネクション数が一番少ないノードに割り振る

  • 最速応答
    一番応答が早いノードに割り振る

  • CPU負荷分散 CPU負荷が一番軽いノードに割り振る

上記方式はいずれも重みづけ(Weight設定)ができる。
これによって優先順位、分散比率を変えることができる。

リクエスト転送方式


  • NAT: IPパケットに対しロードバランサでNATを行ってパケットをサーバに転送

    • この方式は、サーバからのレスポンスもロードバランサを介す。
    • その為、サーバがローカルネットワーク内にある場合等、クライアントとサーバが直接接続出来ない場合でも使える。
    • 経路がLBに限られるので、セキュリティ上も対策しやすく、一般的に使われる。
  • ダイレクトルーティング: IPパケットを書き換えずにサーバに転送

  • トンネリング: IPパケットをカプセル化した上で転送

    • LB-サーバ間でカプセル化されたIPアドレスが使用されるので、LBとサーバが別ネットワークにあっても利用できる。

ダイレクトルーティングとトンネリングはレスポンスはロードバランサを介さない。

セッション維持方法


割愛。
@ITを参照のこと。

一応、軽くセッション管理維持について触れておくと、

負荷分散環境の構築によって、サーバ負荷の軽減やユーザへのスループット向上を実現できる。
参照系のサイトであれば、同一クライアントからの要求をセッションごとにどのサーバに割り振っても特に問題はない。

しかし、ショッピングサイトなどで買い物中に同一クライアントからのセッションが異なるサーバに分散されたのでは、せっかく買おうと思ってショッピングカートに入れた商品が焼失してしまうことになりかねない。

そこで、「セッションの維持が必要」
つまり、同一クライアントからの要求は同一サーバに固定的に割り振るという機能が必要となる。

その実現方法が、IPアドレスをキーにしたり、Http CokkieをキーにしたりSSL Session IDだったりする。
IPアドレスとかだと、プロキシを経由した場合、キーがプロキシのIPになったりして常に同じサーバに接続され、ロードバランサの意味が全くなくなるので注意。

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment