Keepalived と HAProxy による分散高可用性システムの構築

高可用性アーキテクチャの概要

高可用性(High Availability)システムは、複数のサーバーで同一サービスを稼働させ、一台に障害が発生した場合でも自動的に別のサーバーが処理を引き継ぐ仕組みです。これにより、サービスの停止時間を最小限に抑え、継続的な運用を実現します。ここでは、VRRP プロトコルを用いたフェイルオーバーを実現する Keepalived と、ロードバランシングおよびヘルスチェックを行う HAProxy の構成について解説します。

Keepalived によるフェイルオーバー構成

Keepalived は、VRRP(Virtual Router Redundancy Protocol)を利用して仮想 IP アドレスを管理し、マスターノードの障害時にバックアップノードへ IP を移譲します。これにより、クライアントからは単一の IP アドレスとしてサービスが見え、裏側のサーバー切り替えを意識させることなく稼働し続けます。

主要な動作原理

  • heartbeat メカニズム: マスターノードは定期的にマルチキャストで生存信号を送信します。バックアップノードはこの信号を受信できなくなった場合、マスターが障害発生たと判断し、権限を奪取します。
  • 優先度ベースの選出: 複数のノード間でマスターを選出する際、優先度(priority)の高いノードが選定されます。
  • モード: デフォルトの抢占モードでは、優先度の高いノードが復旧すると即座にマスターに戻ります。非抢占モードでは、現在のマスターが完全にダウンするまで切り替えが発生しません。

設定ファイルの構成例 (keepalived.conf)

以下の設定では、仮想 IP に 10.0.0.200 を使用し、インターフェース eth0 をバインドします。マスターノードの優先度を 120、バックアップノードを 100 として設定します。

! Keepalived Configuration
global_defs {
   router_id ha_node_alpha
}

vrrp_script check_web_service {
   script "/usr/local/bin/check_service.sh"
   interval 2
   weight -20
}

vrrp_instance VIP_WEB {
   state MASTER
   interface eth0
   virtual_router_id 51
   priority 120
   advert_int 1
   authentication {
       auth_type PASS
       auth_pass secure_password_2024
   }
   virtual_ipaddress {
       10.0.0.200
   }
   track_script {
       check_web_service
   }
   notify_master "/usr/local/bin/notify_master.sh"
   notify_backup "/usr/local/bin/notify_backup.sh"
}

サービス監視スクリプトの作成

Keepalived 自体はプロセスの監視を行わないため、Web サーバーなどの死活監視スクリプトを用意し、障害時に優先度を下げるか、Keepalived を停止させる必要があります。

#!/bin/bash
# check_service.sh
TARGET_SERVICE="nginx"

if ! pgrep -x "$TARGET_SERVICE" > /dev/null; then
    echo "$(date): $TARGET_SERVICE is down. Stopping keepalived."
    systemctl stop keepalived
    exit 1
fi
exit 0

このスクリプトに実行権限を付与し、設定ファイルの vrrp_script セクションで呼び出すようにします。

脳分裂(Split-Brain)現象への対策

ネットワークの分断などにより、双方のノードが相手を検知できず、同時にマスター権限を取得してしまう現象を脳分裂と呼びます。これを防ぐためには、ファイアウォールで VRRP プロトコル(プロトコル番号 112)の通信を許可し、マルチキャスト通信が阻害されないように設定する必要があります。

firewall-cmd --permanent --add-protocol=vrrp
firewall-cmd --reload

HAProxy によるロードバランシング

HAProxy は、TCP レイヤー(L4)および HTTP レイヤー(L7)で動作する高性能なロードバランサーです。複数のバックエンドサーバーへトラフィックを分散し、ヘルスチェック機能により障害のあるサーバーを自動的にプールから除外します。

主な特徴とアルゴリズム

  • ラウンドロビン (roundrobin): 接続を順にサーバーへ割り振ります。短接続に適しています。
  • leastconn: 現在の接続数が最も少ないサーバーを選択します。長接続に適しています。
  • source: クライアントの IP アドレスに基づいてハッシュ計算を行い、特定のサーバーに固定します。

設定ファイルの構成例 (haproxy.cfg)

グローバル設定でプロセス数と最大接続数を定義し、フロントエンドで受信したリクエストをバックエンドサーバー群へ転送します。統計情報ページも有効化しています。

global
    log 127.0.0.1 local0 notice
    user haproxy
    group haproxy
    daemon
    nbproc 4
    maxconn 2048
    pidfile /var/run/haproxy.pid

defaults
    mode http
    log global
    option httplog
    option dontlognull
    option http-server-close
    retries 3
    timeout connect 5000
    timeout client  30000
    timeout server  30000

listen stats
    bind 0.0.0.0:8404
    mode http
    stats enable
    stats uri /haproxy?stats
    stats refresh 10s
    stats auth admin:secure_admin_pass

frontend http_front
    bind 0.0.0.0:80
    mode http
    option forwardfor
    default_backend web_servers

backend web_servers
    mode http
    balance roundrobin
    option httpchk GET /health
    server web01 192.168.10.11:80 check inter 2000 rise 2 fall 3
    server web02 192.168.10.12:80 check inter 2000 rise 2 fall 3
    server web03 192.168.10.13:80 check inter 2000 rise 2 fall 3 backup

上記の設定では、/health エンドポイントへの HTTP GET リクエストによりバックエンドの死活を確認し、失敗が連続するとトラフィックの送信を停止します。また、backup パラメータが付与されたサーバーは、通常のサーバーが全てダウンした場合にのみ使用されます。

タグ: Keepalived HAProxy VRRP load-balancing high-availability

8月14日 17:25 投稿