编辑:在我写作的时候解决了这个问题:P - 我喜欢那种解决方案。无论如何我想我会发布它,也许别人会遇到同样的问题并找到我的解决方案。不关心积分/业力等等。我刚刚写完了整个事情,所以我想发布它和解决方案。
我有一个SQS FIFO队列。它正在使用死信队列。以下是它的配置方式:
我有一个生产者微服务,我有10个ECS图像作为消费者运行。
出于商业原因,我们必须处理接近它们在队列中传递时间的消息。
我们正在为生产者和消费者代码使用最新版本的AWS SDK Golang客户端软件包(如果重要的话,我可以查看版本,但它并不是非常过时的。)
我捕获了生产者的日志,因此我确切地知道消息何时被放入队列以及消息是什么。
我捕获了所有消费者的聚合日志,因此我可以全面了解所有10个消费者以及收到和处理消息的时间。
以下是我在正常情况下看到的日志:
但我现在看到的问题是某些消息没有得到及时处理。偶尔我们故意处理消息故意处理该消息的系统状态b / c(例如,用户仍然可以登录,因此它应该退回并重试......它会这样做)。问题是如果消费者通知消息,导致队列停止向任何其他消费者发送任何其他消息。
“无法处理消息”这里只是意味着收到了消息,但消费者声明它失败了,所以我们只记录错误,不要继续从队列中删除它。因此,可见性超时(此处为5m)将过期,并将重新传递给另一个消费者并重试最多10次,之后将进入死信队列。
钻研日志并分析后,这就是我所看到的:
我读过的所有文档告诉我队列应该不这样做,但我已经在日志中多次验证了它。遗憾的是,我们没有付费的AWS支持计划,或者我会向他们提交一张票。但只考虑我们有10个独立的消费者都从同一个队列中读取的事实。他们只从这个队列中读取。我们没有任何其他正在使用的队列。
对于重复数据删除,我们使用邮件正文的自动哈希。消息是小型JSON文档。
我的期望是,如果我们有一条导致可见性超时的错误消息,那么当有可用的消费者时,队列仍然可以愉快地提供其可用的任何其他消息。
答案 0 :(得分:5)
好的,事实证明我错过了文档中关于FIFO队列的这一小块信息:
https://docs.aws.amazon.com/AWSSimpleQueueService/latest/SQSDeveloperGuide/FIFO-queues.html
当您收到带有消息组ID的消息时,不再有消息 除非您删除,否则将返回相同的消息组ID 消息或它变得可见。
我确实使用了相同的消息组ID。没有再考虑一下。请注意,如果您这样做并且您的任何一条消息都无法处理,它将备份队列中的所有其他消息,直到消息最终被处理为止。我的解决方案是更改消息组ID。有一些业务逻辑ID,我可以在其上使用postfix,这对我有用。