使用RabbitMQ DLX队列

时间:2017-08-10 13:59:52

标签: rabbitmq queue priority-queue

我有2个RabbitMQ队列:

  • incoming_message =>在哪里我推送我想要稍后处理的所有消息
  • incoming_message_dlx =>我在哪里推送处理失败的消息

正如您的名字一样,incoming_message_dlx队列使用Dead Letter Exchange功能,这意味着当邮件过期时,它将重新排队到我的incoming_message

我尝试实现的是每次处理失败时增加expiration消息,并将它们推送到DLX队列。

问题是,即使邮件已过期,它也不会重新排队到我的incoming_message,而它不在队列的底部(头部)。因此,如果DLX队列中有一个消息的过期时间为7天,并且我们将新消息排入时间为5秒,则此消息将仅在7天+ 5之后重新排队到incoming_message秒...

我在文档中发现我可以将我的DLX队列用作priority queue并根据到期时间优先处理我的消息,但是它没有按预期工作,优先级似乎是被忽略了。

然而,当我使用RabbitMQ管理员(管理插件)并且我得到队列的第一条消息时,它始终是具有更高优先级的消息,但DLX队列的“内部消费者”似乎忽略了此优先级

你知道可能是什么问题吗?

提前多多感谢。

PS:我正在使用RabbitMQ服务器版本3.6.10。

1 个答案:

答案 0 :(得分:0)

  1. 作为队列结构(fifo),rabbitmq确实从队列的开头过期。
  2. 队列ttl包含3种类型:
    • Per-Queue Message TTL:x-message-ttl
    • 每条消息的TTL:有效期
    • 队列TTL:x过期

当您希望邮件仅传递ttl值时,请尝试使用多级ttl队列。

您可以根据需要预定义一些dlx队列。

例如:您希望错误消息在(5s,15s,60s)中重试,您可以通过设置不同的x-message-ttl值来定义3个dlx队列,并将这3个incoming_message_dlx队列绑定dlx路由器到incoming_message;

但是,如果您有一条消息ttl = 30s,则只需使用ttl(5s,15s,60s)预定义3队列,那么在哪里传递?尝试priority queue

  

官方文档

     

应过期的邮件仍仅从head of the queue过期。这意味着与普通队列不同,   甚至per-queue TTL也会导致expired lower-priority messages落后stuck   non-expired higher priority个。   这些消息将永远不会传递,但会显示在队列统计信息中。

expired lower-priority messages落后stucknon-expired higher priority

不会发生像[60s(p = 1),30s(p = 0)]这样的队列!

我们定义了3个队列ttl(5s,15s,60s),为了防止较低的ttl消息被卡住,我们将消息以flor ttl而不是ceil ttl推送到队列;

因此ttl = 30s将传递到ttl = 60s并设置优先级= 1的队列

  • ttl = 30s在预定义的队列之间(15s,60s);
  • 设置ttl = 60s队列的最大优先级= 1,默认值为0;
  • 以优先级= 1传送ttl = 30s消息;

所以队列中的消息就像[30,60,60,60,60]。
ttl = 30s不会被ttl = 60s阻止。