4. 告警源配置:三条核心管道

告警源配置,说白了就是决定“谁来触发后续的动作”。

我个人习惯把 KMS 告警源分成三类:日志驱动(CloudWatch)、事件驱动(EventBridge)、合规驱动(Config)。

它们不是互斥的,经常混合使用。但我建议你先把每种配置方法搞懂,再考虑组合。

KMS 告警源配置三层结构 KMS 审计日志 / 配置变更 CloudWatch Logs 日志指标筛选 → 告警 EventBridge 实时事件匹配 → 调用 AWS Config 合规规则 → 自动修复 CLI 告警 / SNS 通知 或 Lambda 响应 目标触发:SNS / Lambda Step Functions 自动修复 / 合规告警 冗余键删除 建议:生产环境同时启用至少 2 种告警源 CloudWatch 覆盖日志基线,EventBridge 覆盖实时异常,Config 覆盖合规。

4.1 CloudWatch 规则配置

CloudWatch 做 KMS 告警,核心手段是 日志指标筛选。

KMS 会把所有密钥操作记录到 CloudTrail,再送到 CloudWatch Logs 组。你需要创建一个指标筛选器,匹配特定模式,比如 InvalidKeyUsage 或 DisabledKey。

关键概念: CloudWatch 不直接读 CloudTrail 事件,它只盯着 Log Group 里的日志流。所以第一步是确保 KMS 日志正确入组。

我简单列一下步骤(以 kms:ScheduleKeyDeletion 为例):

  1. 在 CloudWatch 控制台,进入日志组 /aws/cloudtrail/kms。
  2. 点击“创建指标筛选器”。
  3. 筛选模式写成:{ $.eventSource = "kms.amazonaws.com" && $.eventName = "ScheduleKeyDeletion" }
  4. 分配指标命名空间 KMS/Audit、指标名 ScheduleKeyDeletionCount。
  5. 基于这个指标创建告警:阈值 ≥ 1,持续 1 个评估周期。
# 等效 CLI 命令(创建指标筛选器)
aws logs put-metric-filter \
  --log-group-name /aws/cloudtrail/kms \
  --filter-name KmsScheduleKeyDeletion \
  --filter-pattern '{ $.eventSource = "kms.amazonaws.com" && $.eventName = "ScheduleKeyDeletion" }' \
  --metric-transformations \
      metricName=ScheduleKeyDeletionCount,metricNamespace=KMS/Audit,metricValue=1

我曾经在生产环境踩过一个坑:筛选模式写得太宽了,导致所有 KMS 调用都计入指标,告警轰炸。后来我们强制要求每个筛选器都加 $.eventName 精确匹配,才消停下来。

技巧: 指标筛选器本身不产生费用,但后续的告警和 API 调用要收费。建议把同类型的多个事件合并到一个筛选器里(例如 DisableKey + ScheduleKeyDeletion 放在同一个 filter),减少告警数量。

4.2 EventBridge 规则配置

EventBridge 比 CloudWatch 更灵活,它能直接匹配 CloudTrail 事件的完整 JSON 结构,还能做 复杂条件(比如忽略某些来源)。

对比项CloudWatch 日志指标EventBridge 规则
触发延迟日志投递后 1-2 分钟几乎实时(秒级)
支持条件简单的文本模式匹配完整 JSON 匹配 + 多条件嵌套
目标类型SNS / SQS / 告警动作SNS / Lambda / Step Functions / SSM
典型场景基线监控、趋势告警实时拦截、自动响应

我个人习惯把 EventBridge 作为 第一道防线。比如有人试图禁用一个正在使用的 CMK,我希望能秒级触发 Lambda 去恢复状态。

配置一个 EventBridge 规则的要点:

  1. 事件总线选 default(除非你使用跨账户事件)。
  2. 在“事件模式”里选 按自定义模式匹配。
  3. 输入以下 JSON(以禁用密钥告警为例):
{
  "source": ["aws.kms"],
  "detail-type": ["AWS API Call via CloudTrail"],
  "detail": {
    "eventSource": ["kms.amazonaws.com"],
    "eventName": ["DisableKey", "ScheduleKeyDeletion"]
  }
}

嗯,这里要注意:EventBridge 的匹配是精确的,如果 eventName 写错一个大小写,规则就永远不会触发。我以前遇到过同事把 DisableKey 写成 disableKey,白跑了一周才发现。

警告: EventBridge 的免费额度是每月 100M 匹配事件,超出后按百万事件计费。如果你的 KMS 调用量极大(比如加密解密的流量进出),建议先估计一下每日事件量,避免月底账单爆炸。

4.3 AWS Config 规则配置

AWS Config 和其他两个不太一样。它不是监控 API 调用,而是检查 KMS 资源的 配置状态。

比如:

  • 密钥是否启用了自动轮转?
  • 密钥是否标签合规?
  • 有没有密钥被禁用超过 30 天?

AWS Config 提供了一些 托管规则,但说实话,大部分 KMS 的合规检查需要你写自定义规则(Lambda 函数)。

配置一个自定义 Config 规则的大概步骤:

  1. 写一个 Lambda 函数,接受 Config 的评估请求。
  2. 函数里用 boto3 调用 KMS API 获取密钥属性。
  3. 返回 COMPLIANT 或 NON_COMPLIANT。
  4. 在 Config 控制台创建自定义规则,关联这个 Lambda。
  5. 设置触发频率(推荐每 6 小时或每天)。
# 自定义 Config 规则 Lambda 骨架(Python)
def evaluate_compliance(config_item):
    key_id = config_item['resourceId']
    client = boto3.client('kms')
    try:
        response = client.describe_key(KeyId=key_id)
        key_state = response['KeyMetadata']['KeyState']
        if key_state == 'Disabled':
            return 'NON_COMPLIANT'
        return 'COMPLIANT'
    except Exception:
        return 'NON_COMPLIANT'

避坑指南: Config 自定义规则的 Lambda 执行时间上限是 30 秒。如果一次要评估几百个密钥,一定要在函数里做分页和超时保护。我曾经有个客户,每天评估 2000 个密钥,结果 Lambda 超时导致一半评估失败。

4.4 三种告警源的协作策略

你不需要在这三个里选一个。实际上,我建议你 全用,但要分工明确:

  • CloudWatch 负责基线监控:比如每小时统计一下禁用密钥的数量变化,超过基线就通知。
  • EventBridge 负责实时响应:比如有人手动禁用生产密钥,立刻触发恢复流程。
  • AWS Config 负责合规审计:每天检查一次是否有不合规的密钥,生成报告并自动化修复。

如果你刚开始搭建这个体系,我建议 先上 EventBridge 做两条关键规则(禁用和删除),再补充 CloudWatch 做趋势监控,最后才上 Config。因为 Config 规则初期配置调试成本高,很容易掉进 Lambda 超时、权限不足的坑里。

最后一张底牌: 不管你用哪种告警源,请确保 告警目标(SNS / Lambda) 已经配置了死信队列或重试策略。告警源本身再可靠,目标挂了也白搭。我遇到过 EventBridge 成功触发了 Lambda,但 Lambda 因为网络故障超时,没有重试,事件就丢了。