当前位置: 首页 > 知识库问答 >
问题:

AWS SQS队列在一条消息的可见性超时到期之前不传递任何消息

魏冷勋
2023-03-14

编辑:在我写的时候解决了这个问题:P--我喜欢这样的解决方案。我想无论如何我都要把它贴出来,也许别人也会有同样的问题,找到我的解决办法。不关心点数/因果报应等等。我只是把整个事情写了出来,所以我想我应该把它和解决方案贴出来。

我有一个SQS FIFO队列。它使用的是一纸空文队列。以下是它的配置方式:

我有一个单一的生产者微服务,我有10个ECS映像运行作为消费者。

由于业务原因,我们在接近消息在队列中传递的时间时处理消息是很重要的。

我们使用AWS SDK Golang客户端包的一个相当新的版本来处理生产者和消费者代码(如果重要的话,我可以去查一下这个版本,但它并不是很过时)。

我为生产者捕获日志,以便准确地知道消息何时被放入队列,以及消息是什么。

下面是我在正常情况下看到的日志:

  1. 在时间x放入队列的消息
  2. 10个使用者之一在时间x接收的消息
  3. 使用者成功处理消息
  4. 使用者在时间x+(0-2秒)从队列中删除的消息
  5. 每天在不同时间重复AdInfinitum,每天最多700条消息

但我现在看到的问题是,有些消息没有得到及时处理。偶尔,我们会在处理一条消息时故意失败,因为系统的状态会影响该消息(例如,可能用户还在登录,所以它应该退后重试……它确实这样做了)。问题是,如果使用者失败了一条消息,它将导致队列停止向任何其他使用者传递任何其他消息。

在深入研究日志并进行分析之后,我看到了以下内容:

  1. 进程开始于上面(生成、消耗、删除消息)。
  2. 使用者在时间x接收的新消息
  3. 使用者失败--记录错误并仅返回(不删除)
  4. 在时间x+5m再次收到相同消息(可见性超时)
  5. 使用者失败--记录错误并仅返回(不删除)
  6. 最多重复10x--消息进入死信队列
  7. 收到新邮件,但现在已晚50分钟!
  8. 现在,在步骤2-7之间放入队列的所有消息都晚了50分钟(5M可见性超时*10次重试)

我读过的所有文档都告诉我队列不应该以这种方式运行,但我已经在日志中验证过几次了。可悲的是,我们没有一个付费的AWS支持计划,否则我会向他们申请一张罚单。但只要考虑一下这样一个事实:我们有10个独立的消费者都在从同一个队列中读取。他们只从这个队列中读取。我们没有它正在使用的任何其他队列。

对于去重复,我们使用消息体的自动散列。消息是小型JSON文档。

我的期望是,如果我们有一个导致可见性超时的坏消息,那么队列仍然会在有可用消费者的情况下愉快地传递它所拥有的任何其他可用消息。

共有1个答案

盖和泰
2023-03-14

好的,结果我错过了文档中关于FIFO队列的一小块信息:

https://docs.aws.amazon.com/awssimplequeueService/latest/sqsdeveloperguide/fifo-queues.html

当您接收到具有消息组ID的消息时,除非您删除该消息或该消息变得可见,否则不会返回相同消息组ID的更多消息。

我确实使用了相同的消息组ID。没有再考虑一下。请注意,如果您这样做,并且您的任何一个消息处理失败,它将备份队列中的所有其他消息,直到消息最终被处理为止。我的解决方案是更改消息组ID。有一些业务逻辑id,我可以在它的后缀,这将为我工作。

 类似资料:
  • 我是AWS的新手。我在这里试图理解SQS。我也看了一些培训,但我仍然不能得到一些答案那里的讨论论坛。我在这里重复我的问题。注意,我知道下面的几个问题有明显的答案,因此更多的是一种修辞。我的困惑源于这样一个事实,即我目前对这个主题的理解导致我对在明显已知的问题之后出现在我脑海中的后续问题给出了相互矛盾的答案,并且夺走了我认为我理解得很好的任何东西的信心。 如果我有一个名为MyQueue的标准队列,并

  • 我对SQS非常陌生,如果我忽略了一些显而易见的事情,我很抱歉,但是有没有办法获取SQS中消息的当前可见性超时?我可以在这里看到如何更新超时可见性。但是我没有看到任何关于获取消息当前可见性超时的信息(也许你可以在收到消息时查看)。 我的用例是根据给定消息的当前可见性超时更改可见性超时。这可能吗? (注意:我知道我可以使用近似的接收时间来达到类似的效果,如果不可能获得当前可见性时间,我会走那条路)

  • 这是关于一个特定的用例,我计划通过flink流来解决这个用例。 一个消息被发送到flink流处理,流被键控,从而得到预期的分区。然而,每个密钥的每个消息都需要评估,直到满足一个条件为止,例如,假设有一个银行系统,其中一个帐户的帐户交易(消息)需要按顺序处理,并且不可能处理不按顺序处理的消息,因为它将导致不一致的系统状态。系统需要等待一条消息被处理(甚至可能超过2-3天),然后再按顺序处理下一条消息

  • 在AWS SQS FIFO的队列中;当读取消息的可见性超时时,队列的哪个位置将是消息? 例如: [A,B]按顺序排列 我从队列中读到一条消息,因此得到消息“a” 消息“A”的可见性超时过期,消费者可以再次使用该消息 消息的新顺序是什么? a)[A, B, C, D] b)[B, C, D, A]

  • 我正在使用AWS sdk开发基于SQS的队列pub-sub。 在非常基本的原型中,我将消息并发地推送到我已经创建的队列中。但是,如何才能确定我的消息正在被推送到队列中呢?

  • 我有一个应用程序,我想使用队列A中的消息,但是如果队列A是空的,我希望它使用队列B中的消息,而不是闲置。我只希望它一次处理一条消息,如果使用者正忙于处理一条消息(来自任一队列),那么其他挂起的消息(在任一队列中)应该保留在他们的队列中,直到使用者再次空闲(这给其他使用者一个机会来处理新的消息)。 例如,如果一条消息在使用者空闲(等待)时到达队列a或队列B,那么使用者就会拾取它。如果在使用者当前正在