AWSのALBで負荷分散を実践
サーバー負荷分散技術の基本は「宛先NAT」。宛先NATはNATの一種で、パケットの宛先IPアドレスを変換する技術。負荷分散装置は、クライアントからパケットを受け取ると、サーバーの稼働状況やコネクション数を確認し、最適なサーバーのIPアドレスに変換する。
ただし、ダウンしているサーバーにパケットを割り振っても意味がない。応答がないだけ。負荷分散装置は、サーバーに対して定期的に監視パケットを送ることで稼働状況を確認し、ダウンと判断されたサーバーを負荷分散対象から除外する。これを「ヘルスチェック」と呼ぶ。
今回は、こうした負荷分散技術について、AWSのALB(Application Load Balancer)を簡単にだが構築して実践してみる。
1. VPCの作成
- AWSマネジメントコンソールで「VPC」サービスに移動
- 「VPCを作成」を選択
- 名前タグ:
MyALBVPC
- IPv4 CIDR ブロック:
10.0.0.0/16
- 「VPCのみ」を選び「作成」
2. サブネットの作成
2-1. サブネット1(後のWebサーバ用)
- 「サブネット」→「サブネットを作成」
- 名前タグ:
WebSubnet1
- VPC:
MyALBVPC
- アベイラビリティゾーン(AZ):
ap-northeast-1a
など - IPv4 CIDR ブロック:
10.0.1.0/24
- 作成
2-2. サブネット2(冗長性確保)
- 名前タグ:
WebSubnet2
- VPC:
MyALBVPC
- アベイラビリティゾーン(AZ):
ap-northeast-1c
など - IPv4 CIDR ブロック:
10.0.2.0/24
- 作成
可用性向上のため、マルチAZ(複数のAZに配置)にするのが一般的。この構成なら、一部のAZに障害が発生しても他のAZのターゲットでリクエストを処理できる。また、ALB自体もマルチAZ構成で動作するため、高い可用性と冗長性が得られる。
3. インターネットゲートウェイ(IGW)の作成・アタッチ
- 「インターネットゲートウェイ」→「作成」
- 名前タグ:
MyALBIGW
- 作成したIGWを選択し、「アクション」→「VPCにアタッチ」
- 対象VPC:
MyALBVPC
4. ルートテーブルの設定
4-1. Webサブネット用ルートテーブル
- 「ルートテーブル」→「作成」
- 名前タグ:
WebRouteTable
- VPC:
MyALBVPC
- 「ルート」タブ→「ルートの追加」
- 送信先:
0.0.0.0/0
- ターゲット:IGW(
MyALBIGW
)
- 「サブネットの関連付け」で
WebSubnet1
とWebSubnet2
を関連付け
5. セキュリティグループの作成
5-1. ALB用SG
- 「セキュリティグループ」→「作成」
- 名前タグ:
ALBSG
- インバウンドルール:
- タイプ:HTTP
- ポート:80
- ソース:
0.0.0.0/0
5-2. EC2(Web)用SG
- 名前タグ:
WebSG
- インバウンドルール:
- タイプ:HTTP
- ポート:80
- ソース:
ALBSG
(セキュリティグループを指定)
- 必要ならSSH(22)も自分のIPだけ許可
6. WebサーバEC2(2台)の作成
6-1. 1台目
- 「EC2」→「インスタンスを起動」
- 名前:
WebServer1
- AMI:Amazon Linux 2
- インスタンスタイプ:t2.micro
- VPC:
MyALBVPC
- サブネット:
WebSubnet1
- パブリックIP自動割当:有効
- セキュリティグループ:
WebSG
- 「高度な詳細」→「ユーザーデータ」欄に以下を貼り付け
#!/bin/bash
echo "Hello from WebServer1" > /var/www/html/index.html
yum install -y httpd
systemctl start httpd
systemctl enable httpd
6-2. 2台目
- 名前:
WebServer2
- サブネット:
WebSubnet2
- セキュリティグループ:
WebSG
- 「高度な詳細」→「ユーザーデータ」欄に以下を貼り付け
echo "Hello from WebServer2" > /var/www/html/index.html
7. ALB(Application Load Balancer)の作成
- 「EC2」→「ロードバランサー」→「ロードバランサーを作成」
- 「Application Load Balancer」を選択
- 名前:
MyALB
- スキーム:インターネット向け
- リスナー:HTTP(80)
- VPC:
MyALBVPC
- アベイラビリティゾーンとサブネット:
WebSubnet1
とWebSubnet2
を選択 - セキュリティグループ:
ALBSG
を指定
8. ターゲットグループの作成
ALB配下の負荷分散先リソースを「ターゲット」、それらを管理する単位を「ターゲットグループ」と呼ぶ。
ターゲットにはインスタンス、IPアドレス、Lambda関数を指定できる。ターゲットグループ単位で負荷分散を行い、適切なターゲットにリクエストがルーティングされるようになる
ALBはターゲットグループ内の各ターゲットが正常に動作しているかを定期的にヘルスチェックで確認する。正常な応答(HTTPステータス200番台)を返せば「healthy」、そうでなければ「unhealthy」と判定され、自動でルーティング対象から外れる。なお、ELBのヘルスチェックには復旧機能がないため、Auto Scalingなどでターゲット数を維持する設計が必要。
-
名前:
MyTargetGroup
-
タイプ:「インスタンス」
-
プロトコル:HTTP
-
ポート:80
-
VPC:
MyALBVPC
-
ヘルスチェックの設定
- プロトコル:HTTP
- パス:
/
- デフォルトでは「/」(ルートパス)が使われる
- (オプション)間隔やタイムアウトも調整可能
- ヘルスチェック間隔:30秒
- タイムアウト:5秒
- しきい値(失敗/成功回数):デフォルト値でOK
- ポイント:
- ターゲットグループ内のEC2がこのパスに正常な応答(200番台)を返していれば「healthy(正常)」扱いになる
- 応答がなければ「unhealthy(異常)」として自動的に振り分け対象から外される
-
登録ターゲットで
WebServer1
とWebServer2
を両方選択→「登録」
9. 動作確認
- 「ロードバランサー」一覧から、作成したALBの「DNS名」をコピー
- ブラウザでアクセス
- ページをリロードすると
Hello from WebServer1
-
Hello from WebServer2
が交互に表示される
おお〜…!
これで、ALBによるサーバー負荷分散の基本的な構成と動作確認までを一通り実践できた。あとはこの基盤をベースに、スケーラビリティや自動復旧といったより実践的な設計へと発展させていけばいい。
Discussion