事件重试策略和使用死信队列 - Amazon EventBridge
Amazon Web Services 文档中描述的 Amazon Web Services 服务或功能可能因区域而异。要查看适用于中国区域的差异,请参阅 中国的 Amazon Web Services 服务入门 (PDF)

本文属于机器翻译版本。若本译文内容与英语原文存在差异,则一律以英文原文为准。

事件重试策略和使用死信队列

有时,事件无法成功传送到规则中指定的目标。例如,当目标资源不可用、 EventBridge 缺乏对目标资源的权限或由于网络状况而导致时,就会发生这种情况。如果由于可重试的错误而无法成功将事件传送到目标,则 EventBridge 会重试发送该事件。您可以在目标的重试策略设置中设置尝试的时间长度和重试次数。默认情况下, EventBridge 会重试发送事件 24 小时,最多 185 次,并出现指数级退缩和抖动或随机延迟。如果在用尽所有重试尝试后仍未传送事件,则该事件将被丢弃,并且 EventBridge不会继续处理该事件。为避免在事件未能传送到目标后丢失事件,您可以配置死信队列 (DLQ),并将所有失败事件发送到该队列,以便日后处理。

EventBridge DLQ 是标准的 Amazon SQS 队列 EventBridge ,用于存储无法成功传送到目标的事件。创建规则并添加目标时,可以选择是否使用 DLQ。配置 DLQ 时,可以保留任何未成功传送的事件。然后,您可以解决导致事件传送失败的问题,并在之后处理事件。

事件错误的处理方式不同。有些事件会在不进行任何重试的情况下被丢弃或发送到 DLQ。例如,由于缺少对目标的权限或目标资源已不存在而导致的错误,在采取行动解决潜在问题之前,所有重试尝试都将失败。与其重试,不如 EventBridge 将这些事件直接发送到 DLQ(如果有的话)。

当事件交付失败时,会向 Amazon CloudWatch 指标 EventBridge 发布一个表明目标invocation失败的事件。如果您使用 DLQ,则会将其他指标发送到 CloudWatch包括InvocationsSentToDLQ和。InvocationsFailedToBeSentToDLQ

您的 DLQ 中的每条消息都将包含以下自定义属性:

  • RULE_ARN

  • TARGET_ARN

  • ERROR_CODE

    以下是 DLQ 可能返回的错误代码示例:

    • CONNECTION_FAILURE

    • CROSS_ACCOUNT_INGESTION_FAILED

    • CROSS_REGION_INGESTION_FAILED

    • ERROR_FROM_TARGET

    • EVENTS_IN_BATCH_REQUEST_REJECTED

    • EVENTS_IN_BATCH_REQUEST_REJECTED

    • FAILED_TO_ASSUME_ROLE

    • INTERNAL_ERROR

    • INVALID_JSON

    • INVALID_PARAMETER

    • NO_PERMISSIONS

    • NO_RESOURCE

    • RESOURCE_ALREADY_EXISTS

    • RESOURCE_LIMIT_EXCEEDED

    • RESOURCE_MODIFICATION_COLLISION

    • SDK_CLIENT_ERROR

    • THIRD_ACCOUNT_HOP_DETECTED

    • THIRD_REGION_HOP_DETECTED

    • THROTTLING

    • TIMEOUT

    • TRANSIENT_ASSUME_ROLE

    • UNKNOWN

  • ERROR_MESSAGE

  • EXHAUSTED_RETRY_CONDITION

    可能返回以下条件:

    • MaximumRetryAttempts

    • MaximumEventAgeInSeconds

  • RETRY_ATTEMPTS

以下视频介绍了 DLQ 的设置:

使用死信队列的注意事项

为配置 DLQ 时,请考虑以下几点。 EventBridge

  • 仅支持标准队列。你不能在中使用 FIFO 队列来获取 DLQ。 EventBridge

  • EventBridge 消息中包含事件元数据和消息属性,包括:错误代码、错误消息、用尽重试条件、规则 ARN、重试尝试和目标 ARN。您可以使用这些值来识别事件和失败原因。

  • 同一账户中 DLQ 的权限:

    • 如果您使用控制台向规则添加目标,并在同一个账户中选择一个 Amazon SQS 队列,则会将授予您 EventBridge 访问该队列的基于资源的策略附加到该队列中。

    • 如果您使用 EventBridge API 的PutTargets操作为规则添加或更新目标,并且在同一账户中选择了 Amazon SQS 队列,则必须手动向所选队列授予权限。要了解更多信息,请参阅为死信队列授予权限

  • 使用不同 Amazon 账户的 Amazon SQS 队列的权限。

    • 如果您通过控制台创建规则,则不会显示其他账户的队列供您选择。您必须提供其他账户中队列的 ARN,然后手动附加基于资源的策略,为该队列授予权限。要了解更多信息,请参阅为死信队列授予权限

    • 如果您使用 API 创建规则,则必须手动将基于资源的策略附加到用作死信队列的另一账户中的 SQS 队列。要了解更多信息,请参阅为死信队列授予权限

  • 您使用的 Amazon SQS 队列必须位于创建规则的区域。

为死信队列授予权限

当您为规则的目标配置 DLQ 时, EventBridge 会将调用失败的事件发送到选定的 Amazon SQS 队列。要成功将事件传送到队列, EventBridge 必须具有执行此操作的权限。当您使用 EventBridge 控制台为规则配置目标并选择 DLQ 时,权限会自动添加。如果您使用 API 创建规则,或者使用其他 Amazon 账户中的队列,则必须手动创建授予所需权限的基于资源的策略,然后将其附加到队列。

以下基于资源的策略演示了如何授予向 Amazon SQS 队列发送事件消息所需的权限。 EventBridge 策略示例向 EventBridge 服务授予使用该SendMessage操作向名为 “MyEventDLQ” 的队列发送消息的权限。队列必须位于 us-west-2 区域,账户为 123456789012 Amazon 。该Condition声明仅允许来自名为 “MyTestRule” 的规则的请求,该规则是在 us-west-2 地区创建的,账户为 123456789012。 Amazon

{ "Sid": "Dead-letter queue permissions", "Effect": "Allow", "Principal": { "Service": "events.amazonaws.com" }, "Action": "sqs:SendMessage", "Resource": "arn:aws:sqs:us-west-2:123456789012:MyEventDLQ", "Condition": { "ArnEquals": { "aws:SourceArn": "arn:aws:events:us-west-2:123456789012:rule/MyTestRule" } } }

要将策略附加到队列,请使用 Amazon SQS 控制台,打开队列,然后选择访问策略并编辑该策略。您也可以使用 Amazon CLI,了解更多信息,请参阅Amazon SQS 权限

如何从死信队列中重新发送事件

可以通过两种方式将消息移出 DLQ:

  • 避免编写 Amazon SQS 使用者逻辑 - 将 DLQ 设置为 Lambda 函数的事件源以耗尽 DLQ。

  • 编写 Amazon SQS 使用者逻辑 — 使用 Amazon SQS API Amazon 、SDK Amazon CLI 或编写自定义使用者逻辑,用于轮询、处理和删除 DLQ 中的消息。