为什么我的 Lambda 函数重试有效的 Amazon SQS 消息并将它们放入我的死信队列中?

1 分钟阅读
0

我将我的 AWS Lambda 函数配置为处理 Amazon Simple Queue Service (Amazon SQS) 队列中的消息。我的一些有效的 Amazon SQS 消息在达到 maxReceiveCount 之前会被多次接收,最后进入我的死信队列。

简短描述

如果您的 Lambda 函数在读取 Amazon SQS 消息批量时受到限制、返回错误或不响应,则消息将返回您的队列。出现可见性超时后,您的 Lambda 函数会再次接收消息批处理。如果您的函数多次无法处理有效消息,则 Amazon SQS 会将消息发送到您的死信队列(如果您已配置死信队列)。

为了防止将有效消息置于死信队列中,您的函数代码必须是幂等且能够多次处理消息。有关更多信息,请参阅如何防止 Amazon SQS 消息多次调用我的 Lambda 函数?

解决方法

验证您的 Lambda 函数的代码是否为幂等

有关幂等性最佳实践和示例函数逻辑,请参阅如何使我的 Lambda 函数为幂等?

确认您的 Amazon SQS 队列的可见性超时时间至少比您的 Lambda 函数的超时设置长六倍

将源队列的可见性超时设置为至少比函数超时长六倍。如果函数在处理前一个批处理时受到限制,则额外的时间允许您的函数重试处理批处理。

有关更多信息,请参阅 Amazon SQS 开发人员指南中的设置可见性超时

**请注意:**如果您的函数因为队列的可见性超时时间不够长而未收到消息,则消息将不会记录在您的 Amazon CloudWatch Logs中。

验证源队列的重新驱动策略中的 maxReceiveCount 属性是否设置为至少五个

将源队列重新驱动策略上的 maxReceiveCount 设置为至少五个。如果您的函数返回错误,或者因为它处于最大并发而无法调用,则处理可能会成功,但需要额外的尝试。maxReceiveCount 至少为五会让您的消息在发送到死信队列之前有更多的机会被处理。

要更新最大并发设置限制,请参阅为 Amazon SQS 事件源配置最大并发

有关更多信息,请参阅《Amazon SQS 开发人员指南》中的死信队列如何工作?避免消息处理不一致

检查 Lambda 函数是否存在限制和预留并发

Lambda 函数有时会受到限制,以保护您的资源和下游应用程序。尽管 Lambda 会自动扩展以适应传入流量,但您的函数仍可能由于各种原因受到限制。

使用[ Lambda 控制台检查预留并发的设置](https://console.aws.amazon.com/lambda/)。如果未配置预留并发,则该函数使用非预留并发。当函数调用超过非预留并发时,就会出现限制。

**请注意:**如果您配置的函数的预留并发为零,则该函数会受到限制,因为它无法处理任何事件。请确保将该值增加到一个大于零的数字。

如果同一 AWS 区域中的其他函数使用并发限制,则可能会出现限制。受到限制的 Lambda 函数会将 SQS 消息发送到死信队列。

避免重新处理失败的批处理中的所有 SQS 消息

所有 SQS 消息在处理批处理时遇到错误的 Lambda 函数的死信队列中都可见,包括 Lambda 成功处理的消息。然后,Lambda 再次重试整批 SQS 消息。

为避免重新处理失败的批处理中的所有 SQS 消息,请使用 FunctionResponseTypes 列表中的 ReportBatchItem Failles 值配置事件源映射。这可以让您的函数返回部分成功消息并减少重试次数。有关更多信息,请参阅报告批处理项目故障

识别并解决您的 Lambda 函数返回的任何错误

按照《如何解决 Lambda 函数故障?》中的说明进行操作只有当函数没有返回错误时,您的函数才会自动从队列中删除消息。

相关信息

如何请求提高我的 Lambda 函数的并发限制?

如何解决带有“超出速率”和 429 “TooManyRequestsException”错误的 Lambda 函数限制问题?

AWS 官方
AWS 官方已更新 1 年前