如何将非告警类AWS SNS主题订阅至PagerDuty集成?
问题:非CloudWatch告警类SNS消息投递至PagerDuty的实现方案?
问题背景
已知CloudWatch告警可触发PagerDuty告警,且告警恢复时能自动解决PagerDuty事件;这类CloudWatch告警对应的SNS主题负载包含PagerDuty集成预期的message结构。
当前需求是将非CloudWatch告警类的SNS主题(例如由DMS复制任务事件触发的SNS主题)直接绑定到PagerDuty的CloudWatch API集成,但配置完成后始终无法接收消息。想确认:
- 是否必须使用CloudWatch告警的负载格式才能触发PagerDuty?
- 有无无需额外处理的直接投递方案?
- 目前想到的替代方案是用Lambda转换消息格式后转发到绑定PagerDuty的SNS主题,是否存在更优方案?
编辑补充:提供的Terraform配置本身无问题,无法接收消息的原因是管理员未将消息转发至集成验证的目标位置,修正后配置可正常运行。
核心解答
1. PagerDuty CloudWatch集成的格式要求
PagerDuty的CloudWatch专用集成确实依赖特定的负载结构(包含message对象),非CloudWatch生成的SNS消息(如DMS直接发送的消息)因格式不匹配,无法被该集成正确解析,因此无法触发告警。
2. 可行方案对比
方案一:Lambda转换负载(原设想方案)
这是成熟的兼容方案:
- 将DMS的SNS主题订阅至Lambda函数
- 在Lambda中把DMS原始消息结构转换为PagerDuty CloudWatch集成期望的格式
- 转换完成后发送至绑定PagerDuty端点的SNS主题(或直接调用PagerDuty API)
- 优点:完全可控,可自定义告警内容、恢复逻辑;缺点:需要额外维护Lambda代码及权限配置
方案二:使用PagerDuty通用事件API集成(更优方案)
无需模拟CloudWatch格式,直接通过PagerDuty通用事件API对接:
- 在PagerDuty中创建通用事件API集成(而非CloudWatch专用集成)
- 将SNS主题的HTTPS订阅指向该通用集成的端点
- 按需配置SNS消息过滤/转换,确保消息包含通用API要求的核心字段(如
payload.summary、dedup_key) - 优点:无需中间Lambda中转,直接对接;支持适配各类SNS消息源,还可自定义告警内容;若需自动恢复事件,只需在恢复消息中携带对应
dedup_key即可
3. 原配置验证结论
你提供的Terraform配置逻辑正确,故障根源在于管理员侧的消息转发配置问题,修正转发路径后即可正常触发PagerDuty告警。
配置所用Terraform代码
locals{ pagerduty_alerts_endpoint = "https://events.pagerduty.com/integration/xxxx/enqueue" } resource "aws_sns_topic" "dms_repl_tasks_topic_pagerduty" { name = "dms-repl-tasks-topic-pagerduty-${local.namespace_coalesce}" delivery_policy = local.sns_delivery_policy_pagerduty tags = merge(local.common_tags, local.migrated_tags, tomap({ "Name" = "dms-repl-tasks-topic-pagerduty-${local.namespace_coalesce}" })) depends_on = [ aws_dms_replication_instance.dms_instance_on_prem_to_rds ] } resource "aws_sns_topic_subscription" "repl_task_notification_pagerduty_subscription" { count = "${local.pagerduty_alerts_endpoint != "" ? 1 : 0}" topic_arn = aws_sns_topic.dms_repl_tasks_topic_pagerduty.arn protocol = "https" endpoint = "${local.pagerduty_alerts_endpoint}" endpoint_auto_confirms = true depends_on = [ aws_sns_topic.dms_repl_tasks_topic_pagerduty ] } resource "aws_dms_event_subscription" "event_subscription_repl_task_direct" { enabled = true event_categories = ["creation", "failure", "deletion", "state change", "configuration change"] name = "dms-event-sub-repl-task-direct-${local.namespace_coalesce}" sns_topic_arn = aws_sns_topic.dms_repl_tasks_topic.arn source_ids = [for ts in aws_dms_replication_task.onprem_to_rds_replication_task : ts.replication_task_id] source_type = "replication-task" tags = merge(local.common_tags, tomap({ "Name" = "dms-event-sub-repl-task-direct-${local.namespace_coalesce}" })) depends_on = [ aws_dms_replication_task.onprem_to_rds_replication_task, aws_sns_topic.dms_repl_tasks_topic, aws_sns_topic_subscription.repl_task_notification_email_subscription ] timeouts { create = "2m" delete = "2m" update = "2m" } }
内容的提问来源于stack exchange,提问作者Ross Bush
相关产品推荐
相关产品推荐

