AWS WAFルールでのCloudWatch Metricsの設定について

このブログシリーズ 「クラウドセキュリティ 実践集」 では、一般的なセキュリティ課題を取り上げ、「なぜ危険なのか?」 というリスクの解説から、「どうやって直すのか?」 という具体的な修復手順(コンソール、AWS CLI、Terraformなど)まで、分かりやすく解説します。
この記事では、WAF RuleGroup および Ruleに紐づくRuleのすべてにおいてCloudWatch Metricsが有効化されていない状態について、リスクと対策を解説します。

ポリシーの説明
Security Hub コントロール AWS WAF – AWS Security Hub
[WAF.12] AWS WAF ルールでは CloudWatch メトリクスを有効にする必要があります
このコントロールは、 AWS WAF ルールまたは ルールグループで Amazon CloudWatch メトリクスが有効になっているかどうかを確認します。ルールまたはルールグループで CloudWatch メトリクスが有効になっていない場合、コントロールは失敗します。
リスク
AWS WAFは、ウェブアプリケーションやAPIを一般的なウェブ攻撃から保護するウェブアプリケーションファイアウォールです。WAFのRuleGroupやRuleにCloudWatch Metricsが有効化されていない場合、トラフィックの挙動やセキュリティイベントの可視性が失われ、以下のようなリスクが発生します。
- 攻撃の特定と分析の困難化: どのWAFルールが特定の悪意あるリクエストを検知・ブロックしたのか、あるいは許可してしまったのかを把握できません。これにより、SQLインジェクションやXSSなどの攻撃が成功した場合でも、その経路や手口を特定するのが難しくなります。
- セキュリティ体制の評価不足: WAFがどれだけ効果的に機能しているか、またはどのルールが頻繁にトリガーされているかといった情報が得られません。これにより、WAFルールのチューニングやセキュリティ体制の改善に必要なデータが不足します。
- 異常検知の遅延: 通常とは異なるトラフィックパターンや、特定のルールが異常に多くヒットしているといった兆候を、CloudWatch Metricsを介して自動的に検知できません。これにより、進行中の攻撃や設定ミスの発見が遅れる可能性があります。
- コンプライアンス違反: 多くのセキュリティ基準やコンプライアンス要件では、セキュリティログの収集と監視が求められます。WAFメトリクスが有効でない場合、これらの要件を満たすことが困難になることがあります。
- 運用上の非効率性: 問題発生時にWAFのログやメトリクスが不足していると、トラブルシューティングに時間がかかり、運用チームの負担が増加します。
対策
WAF RuleGroup および RuleにCloudWatch Metricsを有効化することは、ウェブアプリケーションのセキュリティ監視を強化し、悪意あるアクティビティを早期に特定するために不可欠です。
- すべてのルールとルールグループでメトリクスを有効化: WAFウェブACL内の個々のルール(AWSマネージドルール、カスタムルール)およびルールグループ(マネージドルールグループ、独自のルールグループ)のすべてでCloudWatch Metricsが有効になっていることを確認します。
- メトリクス名の明確化: 各ルールやルールグループに、識別しやすい明確なメトリクス名を設定します。これにより、どのメトリクスがどのルールに対応しているかを簡単に把握できます。
- CloudWatchアラームの設定: WAFメトリクスに基づいてCloudWatchアラームを設定します。例えば、特定のルールが短期間に大量にヒットした場合や、ブロックされたリクエスト数が異常に増加した場合に通知するように設定します。
- ダッシュボードでの可視化: WAFメトリクスをCloudWatchダッシュボードに追加し、トラフィックの傾向、ブロックされたリクエスト数、許可されたリクエスト数などを視覚的に確認できるようにします。
- ログデータとの連携: CloudWatch Logsに発行されるWAFのフルログ(サンプリングされたリクエストだけでなく)とメトリクスを連携させて分析することで、攻撃の全体像をより詳細に把握できます。
修復方法
AWSコンソールでの修復手順
AWSコンソールを使用して、WAF RuleGroup および RuleのCloudWatch Metricsを有効にします。
- AWS WAFウェブACLの選択:
- AWSコンソールにログインし、AWS WAFサービスを開きます。
- 左側のナビゲーションペインで「ウェブACL」を選択します。
- メトリクスを有効にしたいウェブACLを選択します。
- ルールグループまたはルールの編集:
- ウェブACLの詳細ページで「Logging and metrics」タブを選択します。
- Loggingのフィールドで「Enable」のボタンをクリックし、「Logging destination」を選択
- 編集画面にて「Amazon CloudWatch Logs log group」に「’aws-waf-logs-」から始まるロググループを作成します。
- 作成したロググループを設定し、Redacted fieldsからロギングする対象を選択後、SAVEをクリック。

Terraformでの修復手順
TerraformでWAF RuleGroup および RuleのCloudWatch Metricsを有効化するには、aws_wafv2_web_acl
の rule
ブロック内、または aws_wafv2_rule_group
リソースの rule
ブロック内の visibility_config
を設定します。
# 通知用のSNSトピックを定義
resource "aws_sns_topic" "waf_alert_topic" {
name = "waf-security-alerts"
}
# SNSトピックへのサブスクリプション (例: Eメール)
# ※手動確認 (pending_confirmation) が必要なため、適用後にメール確認が必要です。
resource "aws_sns_topic_subscription" "email_subscription" {
topic_arn = aws_sns_topic.waf_alert_topic.arn
protocol = "email"
endpoint = "your-email@example.com" # あなたのメールアドレスに置き換えてください
}
# WAFv2 ウェブACLの定義
resource "aws_wafv2_web_acl" "example_web_acl" {
name = "my-cloudfront-web-acl"
scope = "CLOUDFRONT" # または "REGIONAL"
description = "Web ACL for CloudFront distribution with all metrics enabled"
default_action {
allow {}
}
# ウェブACL全体のビジビリティ設定 (トップレベルのメトリクス)
visibility_config {
cloudwatch_metrics_enabled = true
metric_name = "CloudFrontWebAclMetrics"
sampled_requests_enabled = true
}
# カスタムルールの定義例 (メトリクスを有効化)
rule {
name = "IPRateLimit"
priority = 10
action {
block {}
}
statement {
# rate_limit_statement を rate_based_statement に修正
rate_based_statement {
limit = 1000
aggregate_key_type = "IP"
}
}
visibility_config {
cloudwatch_metrics_enabled = true
metric_name = "IPRateLimitMetric" # ルールごとのメトリクス名
sampled_requests_enabled = true
}
}
# AWSマネージドルールグループの定義例 (メトリクスを有効化)
rule {
name = "AWS-Managed-CommonRuleSet"
priority = 20
action {
count {} # まずはCountモードでテストを推奨
}
statement {
managed_rule_group_statement {
name = "AWSManagedRulesCommonRuleSet"
vendor_name = "AWS"
}
}
visibility_config {
cloudwatch_metrics_enabled = true
metric_name = "CommonRuleSetMetrics" # ルールグループごとのメトリクス名
sampled_requests_enabled = true
}
}
}
# WAFメトリクスに基づくCloudWatchアラーム
resource "aws_cloudwatch_metric_alarm" "waf_block_alarm" {
alarm_name = "WAF-HighBlockRate-Alarm"
comparison_operator = "GreaterThanThreshold"
evaluation_periods = 1
metric_name = "Count" # マネージドルールグループのブロック数メトリクスは 'Count'
namespace = "AWS/WAFV2"
period = 300 # 5分
statistic = "Sum"
threshold = 50 # 50件以上のブロックでアラーム
# WAFV2メトリクスのdimensionsは以下のようにWebACL名とRuleGroup名を含めます
dimensions = {
RuleGroup = "AWSManagedRulesCommonRuleSet" # マネージドルールグループの名前
WebACL = aws_wafv2_web_acl.example_web_acl.name
# CloudFrontデプロイの場合、Regionは'GLOBAL'になります。
# REGIONALデプロイの場合、そのリージョン名 ('ap-northeast-1' など) になります。
# ここは自動的に設定されるため、明示的に指定しないことが多いです。
}
alarm_description = "High number of requests blocked by WAF Common Rule Set"
alarm_actions = [aws_sns_topic.waf_alert_topic.arn]
ok_actions = [aws_sns_topic.waf_alert_topic.arn]
}
上記の例では、aws_wafv2_web_acl
リソース内の各 rule
ブロック(カスタムルール、マネージドルールグループなど)に visibility_config
ブロックを追加し、cloudwatch_metrics_enabled = true
を設定することで、CloudWatch Metricsを有効化しています。これにより、各ルールやルールグループの評価結果がメトリクスとしてCloudWatchに送信されるようになります。
scope
はCloudFrontにデプロイする場合はCLOUDFRONT
、特定のリージョンにデプロイする場合はREGIONAL
を選択してください。your-email@example.com
やその他のプレースホルダーは、実際の環境に合わせて修正してください。
最後に
こちらの内容の検出は弊社が提供するSecurifyのCSPM機能で簡単に検出及び管理する事が可能です。運用が非常にラクに出来る製品になっていますのでぜひ興味がある方はお問い合わせお待ちしております。
最後までお読みいただきありがとうございました。この記事が皆さんの役に立てば幸いです。