ALBとLambda(python)だけでメンテナンスページ
AWSでRoute53とACMとALBとEC2を使ってSSLにしているWEBアプリケーションで、メンテナンス画面の運用を簡単便利にするため、下記5点をALBとLambda(python)で可能にします。
- メンテナンス画面をALBとLambda(python)で作る
- メンテナンス画面への切替リスクが低くて簡単
- 通常運用ページに戻すリスクが低くて簡単
- Lambdaにメンテナンス画面のhtmlを持たせる/いつでもhtml編集できる
- ALBのリスナーで設定したhttp⇒httpsリダイレクトやACMの証明書などの設定をそのまま使える
ロードバランサーの「リスナー」の「リスナーID」の「https:443」の「ルールの表示/編集」の「ルール」の「転送先」の「ターゲットグループ」で0か1の重み設定だけで簡単にメンテナンスページへ切り替えられるようにします。
そのため、ALBのロードバランサー1台に対して以下2つのターゲットグループをあらかじめ準備して「ルール」の「転送先」に追加したままにしておきます。
- ターゲットの種類がWEBアプリケーションのEC2インスタンスになっている通常運用向けのターゲットグループ
- ターゲットの種類がLambdaとなっているメンテナンス向けのターゲットグループ
キャッシュが邪魔してくることがあるのでブラウザのシークレットウィンドウで検証しながら作業する様にしてください。
このメンテページ方式のデメリットは、html保存はS3にして欲しい!とか、プレビューも見られるようにしたい!っていう話が出ると困るという事です。
「メンテナンス画面への切替」の仕組みを作る手順
ターゲットグループの「ターゲットの種類」でpythonで作った「Lambda関数」を使って「ターゲットグループ」を新しく作る
ロードバランサーの「リスナー」で「ルール」の「HTTPS:443」転送先に新たに作ったLamdaのターゲットグループを「重み:0」で追加する
ELBでターゲットグループを作り、Lambdaも作る
- EC2ダッシュボードへ
- ターゲットグループへ
- 「ターゲットグループの作成」をクリック
- 「ターゲットグループ名」を任意で入力 EX)プロジェクト名-elb-target-lambda
- 「ターゲットの種類」で「Lambda関数」を選択
- 「関数を作成します」をクリック
- 「Serverless Application Repositoryの参照」で「ALB-Lambda-Target-HelloWorld」を検索して選択
- 「AWS Lambda」の「関数」画面で、「アプリケーションの設定」の「アプリケーション名」を「ALB-Lambda-Target-HelloWorld」を任意で書き換える EX)プロジェクト名-ALB-Lambda-Target-Maintenance
- 右下のオレンジ色「デプロイ」をクリック、デプロイが終わるまで待つ
- デプロイが完了したら、元の「ターゲットグループの作成」のページへ戻る
- 作ったLambda関数を選びなおす
- 青いボタンの「作成」をクリック
- 「プロジェクト名-elb-target-lambda」のターゲットグループにチェック
- タブの「ターゲット」をクリック
- 青いボタンの「登録」をクリック
この作業を行うと、CloudFromationスタックも自動で作成されます。
Lambdaのpythonの中のhtmlソースコードを編集する
- Lambdaへ
- 関数へ
- 作成したLambda関数の関数名をクリック
- 画面を下にスクロールして、「関数コード」のエディタで、helloworld_27.pyの11行目から25行目のhtmlをメンテナンスモードで表示したいhtmlに変えます。下記メンテナンスページhtmlを参考にしてもOKです。※Windowsの方は、コピペを Ctrl+C と Ctrl+V で実行できます。マウスの右クリックコピー&ペーストは、関数コードのエディタでは使えません。
- 変えたら、右上のオレンジ色の「Deploy」ボタンをクリック
今回は、「VPC設定」は行いません。
メンテナンスページhtml(参考)
Qiitaからいただいたものをちょっと加工した以下のものでよければご利用ください。インデントが雑ですみません。
<!doctype html>
<html lang="ja">
<head>
<meta charset="utf-8">
<title>◯◯システムメンテナンスのお知らせ</title>
<meta name="description" content="◯◯システムメンテナンスのお知らせ">
<!--[if lt IE 9]>
<script src="https://cdnjs.cloudflare.com/ajax/libs/html5shiv/3.7.3/html5shiv.js"></script>
<![endif]-->
</head>
<body>
<div style='max-width: 600px; margin: 30px auto;'>
<div style='border: 1px solid #ccc; padding: 30px; margin-top: 30px;'>
<h1 style="color: #F00">◯◯システムメンテナンスのお知らせ</h1>
<p>
いつも◯◯システムをご利用いただき、誠にありがとうございます。<br />
このたびサービス向上のため、システムメンテナンスを実施させていただきます。<br />
下記日時はサービスをご利用いただけません。</p>
<ul>
<li>2020/10/13(火)PM11:00~2020/10/14(水)AM3:00</li>
</ul>
<p>お客さまには大変ご迷惑をおかけいたしますが、何卒、よろしくお願い申し上げます。
</p>
</div>
</div>
</body>
</html>
helloworld_27.pyのソースコード(参考)
def lambda_handler(event, context):
response = {
"statusCode": 200,
"statusDescription": "200 OK",
"isBase64Encoded": False,
"headers": {
"Content-Type": "text/html; charset=utf-8"
}
}
response['body'] = """<html lang="ja">
<head>
<meta charset="utf-8">
<title>◯◯システムメンテナンスのお知らせ</title>
<meta name="description" content="◯◯システムメンテナンスのお知らせ">
<!--[if lt IE 9]>
<script src="https://cdnjs.cloudflare.com/ajax/libs/html5shiv/3.7.3/html5shiv.js"></script>
<![endif]-->
</head>
<body>
<div style='max-width: 600px; margin: 30px auto;'>
<div style='border: 1px solid #ccc; padding: 30px; margin-top: 30px;'>
<h1 style="color: #F00">◯◯システムメンテナンスのお知らせ</h1>
<p>
いつも◯◯システムをご利用いただき、誠にありがとうございます。<br />
このたびサービス向上のため、システムメンテナンスを実施させていただきます。<br />
下記日時はサービスをご利用いただけません。</p>
<ul>
<li>2020/10/13(火)PM11:00~2020/10/14(水)AM3:00</li>
</ul>
<p>お客さまには大変ご迷惑をおかけいたしますが、何卒、よろしくお願い申し上げます。
</p>
</div>
</div>
</body>
</html>
"""
return response
※helloworld_27.pyでsyntax errorなどが出る場合。helloworld_27.pyファイルの最初の行に以下1行を追記してみてください。エスケープです。
# coding: UTF-8
ELBのリスナーのルールに作成したLambdaのターゲットグループを追加する
- EC2ダッシュボードへ
- ロードバランサ―へ
- Lambdaのメンテナンスページを使いたいロードバランサーを選択する
- タブで「リスナー」をクリック
- 「HTTPS:443」の「ルールの表示/編集」をクリック
- 画面左上にある鉛筆マーク(ルールの編集)をクリック
- 「最後 HTTPS 443: デフォルトアクション」の左側にある鉛筆マーク(ルールの編集)をクリック
- 「1.転送先」の左側にある鉛筆マークをクリック
- 2つ目のターゲットグループに作成したLambdaを追加、とりあえず、重みは0(ゼロ)にする
- 下部の青い丸のレ点チェックマークをクリック
- 右上の青い「更新」ボタンをクリック。
メンテナンスページへの切替
- EC2ダッシュボードへ
- ロードバランサ―へ
- Lambdaのメンテナンスページを使いたいロードバランサーを選択する
- タブで「リスナー」をクリック
- 「HTTPS:443」の「ルールの表示/編集」をクリック
- 画面左上にある鉛筆マーク(ルールの編集)をクリック
- 「最後 HTTPS 443: デフォルトアクション」の左側にある鉛筆マーク(ルールの編集)をクリック
- 「1.転送先」の左側にある鉛筆マークをクリック
通常運用向けのEC2インスタンス向けのターゲットグループを「重み:0」、メンテナンスモード向けのLambdaのターゲットグループ「重み:1」として設定してください。
※シークレットウィンドウで反映するまで15秒くらいで、やや反映が遅いです。
通常運用への切替
- EC2ダッシュボードへ
- ロードバランサ―へ
- Lambdaのメンテナンスページを使いたいロードバランサーを選択する
- タブで「リスナー」をクリック
- 「HTTPS:443」の「ルールの表示/編集」をクリック
- 画面左上にある鉛筆マーク(ルールの編集)をクリック
- 「最後 HTTPS 443: デフォルトアクション」の左側にある鉛筆マーク(ルールの編集)をクリック
- 「1.転送先」の左側にある鉛筆マークをクリック
通常運用向けのEC2インスタンス向けのターゲットグループを「重み:1」、メンテナンスモード向けのLamdaのターゲットグループ「重み:0」として設定する。
※シークレットウィンドウで反映するまで15秒くらいで、やや反映が遅いです。