Open11
AWSCLIをWAFのカスタムレスポンスでメンテナンス画面を表示する
下記をAWSCLIで実施できるようにする
WAFv2のAWSCLIは下記のコマンドがある
カスタムレスポンスだけを変更するコマンドは無いため、 update-web-acl
で頑張るしか無い
AWSCLIでWAFをアップデートするには下記を参考にする
既にWAFはTerraformで構築済みなので、変更だけであれば下記を実施すれば良い
$ WAF_ACL_NAME='test-waf-acl'
$ WAF_ACL_ID='xxxxxxxxxx'
# 現在のWebACLの設定を取得する
$ aws wafv2 get-web-acl --name "${WAF_ACL_NAME}" --scope=CLOUDFRONT --region us-east-1 --id "${WAF_ACL_ID}" > webacl.json
# JSON内のRulesに追加したいルールを追加する
$ vim webacl.json
# LockTokenを取得する
$ LockToken=$(cat webacl.json | jq -r .LockToken)
# webacl.json からRulesのみ抽出したJSONを生成する
$ cat webacl.json | jq .WebACL.Rules > webacl_rule.json
# WebACLをアップデートする
$ /usr/local/bin/aws --scope=CLOUDFRONT --region us-east-1 wafv2 update-web-acl --name "${WAF_ACL_NAME}" --id "${WAF_ACL_ID}" --rules file://webacl_rule.json --lock-token "${LockToken}" --visibility-config "SampledRequestsEnabled=true,CloudWatchMetricsEnabled=true,MetricName=${WAF_ACL_NAME}-metric" --default-action Allow={}
AWSCLIで実行した場合、結果が長いとページャーが起動する。シェルスクリプトなどスクリプトで実施する場合は --no-cli-pager
を指定する必要がある
今回の環境では別のルールでIP制限を行っていたため、その下にメンテナンス画面用のルールを追記した。具体的に準備した webacl_rule.json
は下記の通りです
webacl_rule.json
[
{
"Name": "BlockIpsExceptWhitelist",
"Priority": 0,
"Statement": {
"NotStatement": {
"Statement": {
"IPSetReferenceStatement": {
"ARN": "arn:aws:wafv2:us-east-1:xxxxxx:global/ipset/allow-ip-limit/xxxxx"
}
}
}
},
"Action": {
"Block": {}
},
"VisibilityConfig": {
"SampledRequestsEnabled": true,
"CloudWatchMetricsEnabled": true,
"MetricName": "BlockIpsExceptWhitelist"
}
},
{
"Name": "EnableMaintenance",
"Priority": 1,
"Statement": {
"NotStatement": {
"Statement": {
"IPSetReferenceStatement": {
"ARN": "arn:aws:wafv2:us-east-1:xxxxxx:global/ipset/allow-ip-maintenance/xxxxxx"
}
}
}
},
"Action": {
"Block": {
"CustomResponse": {
"ResponseCode": 503,
"CustomResponseBodyKey": "maintenance-body"
}
}
},
"VisibilityConfig": {
"SampledRequestsEnabled": true,
"CloudWatchMetricsEnabled": true,
"MetricName": "EnableMaintenance"
}
}
]
上記のJSONを読み込ませたところエラー発生。カスタムレスポンスボディが見つからない様子
$ /usr/local/bin/aws --scope=CLOUDFRONT --region us-east-1 wafv2 update-web-acl --name "${WAF_ACL_NAME}" --id "${WAF_ACL_ID}" --rules file://webacl_rule.json --lock-token "${LockToken}" --visibility-config "SampledRequestsEnabled=false,CloudWatchMetricsEnabled=false,MetricName=${WAF_ACL_NAME}-metric" --default-action Allow={}
An error occurred (WAFInvalidParameterException) when calling the UpdateWebACL operation: Error reason: AWS WAF couldn't find a resource that a parameter references., field: CUSTOM_RESPONSE, parameter: maintenance-body
update-web-acl
のオプションを見ると --custom-response-bodies
がある。カスタムレスポンスでHTMLを指定する場合、ルールと同様に指定が必要そう
カスタムレスポンス用のJSONを準備する
maintenance.json
{
"maintenance-body": {
"ContentType": "TEXT_HTML",
"Content": "<h1>maintenance</h1>"
}
}
下記のコマンドでカスタムレスポンスを設定できた
/usr/local/bin/aws --scope=CLOUDFRONT --region us-east-1 --no-cli-pager wafv2 update-web-acl --name "${WAF_ACL_NAME}" --id "${WAF_ACL_ID}" --rules file://webacl_rule.json --custom-response-bodies file://maintenance.json --lock-token "${LockToken}" --visibility-config "SampledRequestsEnabled=false,CloudWatchMetricsEnabled=false,MetricName=${WAF_ACL_NAME}-metric" --default-action Allow={}
実環境のカスタムレスポンスボディはダブルクォーテーション含んでいる。どのようにカスタムレスポンス用のJSONを生成するのが楽なのか。