过期消息传递序列 RabbitMQ

Posted

技术标签:

【中文标题】过期消息传递序列 RabbitMQ【英文标题】:Expired Message Delivery Sequence RabbitMQ 【发布时间】:2014-11-30 03:20:19 【问题描述】:

我们正在构建一个将消息发布到超时队列的解决方案。在 TTL 到期后,消息被推送到主队列进行重新处理。

我们正在设置计数器值,以便为 x 号尝试消息。重新投递的次数。

解决方案运行良好。但是场景是当头部位置最高的消息 TTL 没有过期时,其他过期时间较低的消息不会被重新发布(到主队列)。

这种理解正确吗?如果是,那么解决方案是什么,以便在 TTL 之后重新处理每条消息。

欣赏答案/观点。

谢谢。

【问题讨论】:

【参考方案1】:

如果您使用每个队列的消息 TTL,则消息会过期并从队列中从头到尾移除(与发布的顺序相同)。

当你使用 per-message TTL 时,只有当消息到达队列头时才会从队列中删除,所以过期消息仍然驻留在队列中间的情况是正常的。此类消息不会发送给消费者,并且会被死信(或丢弃),但由于严格的 FIFO 特性或 RabbitMQ 的队列会如上所述发生,当它们到达队列头时,删除前的延迟可能大于实际消息 TTL .例如,如果有两条消息,第一条 TTL=10 秒,第二条 TTL=1 秒,第二条消息也会在 10 秒内死信,而它会停留在第一条消息之后。

为了处理具有不同 TTL 的消息,常见的解决方法是声明几个队列,每个队列用于具有相同或几乎相同的消息,例如,精度为 10 秒。实际精度可能会有所不同,但它非常特定于应用程序并且具有某种经验值。

如果您要选择单独的每个 TTL 队列,请使用每个队列的 TTL 而不是每个消息的 TTL,以简化消息工作流程并防止在理解消息发生的情况时产生歧义。你之后的开发者会为此感谢你的。

要在消息的 TTL 后重新处理消息,请使用 Dead Letter Exchanges,但要注意循环消息问题:如果 RabbitMQ 代理检测到您的消息工作流循环了(消息在被删除后使用相同的路由密钥发布到相同的交换),它会默默地丢弃消息。

【讨论】:

队列 ttl 足够简单并且工作正常。但按消息设置的 ttl 无法正常工作:每条消息在 ttl 之后发布给在线消费者。为什么rabbitmq提供这个功能?适用于哪种业务场景?【参考方案2】:

队列 ttl 很简单并且工作正常。 但按消息设置的 ttl 无法正常工作:每条消息都在 ttl 之后发布给在线消费者。

为什么rabbitmq提供这个功能?适用于哪种业务场景?

【讨论】:

以上是关于过期消息传递序列 RabbitMQ的主要内容,如果未能解决你的问题,请参考以下文章

RabbitMQ消息队列笔记

RabbitMQ消息队列笔记

消息中间件-----RabbitMq消息可靠传递

用于 FanOut 消息传递的 RabbitMQ 工作队列

RabbitMQ - 消息传递顺序

当 RabbitMQ 交换不存在时如何处理错误(并且消息通过消息传递网关接口发送)