RabbitMQ 在不从消费者发布的情况下重试消息

RabbitMQ retrying messages without publishing from the consumer

我可以重试一条消息 N 次,然后将它发送到死队列而不进行确认并重新发布来自消费者的消息吗?

我能想到的唯一方法是使用带有 dlx 设置的多个队列,它会像这样填充下一个重试队列:

test ---> test.retries.1 ---> ... ---> test.retries.N ---> test.dead

这样可以吗?我不确定我的意思是好的。我最近开始玩rabbitmq。假设这是一个常见的设置?有什么缺点吗?

还有别的办法吗?也许是一个插件,它向 basic.reject 添加一个计数器并做同样的事情?


旁注:我想知道这一点,因为我不相信让消费者确认消息(即使他无法处理消息)然后再次发布消息的想法。最后你会得到多个 liers,它们会发布一条消息,并且不时地在其他人之前立即获取它 "just to be sure" 并且..你会让他们记住..(他们不会)[这也发生在具有多个重试队列的场景中,但至少代理将控制消息的去向而不是消费者]

basic.reject with requeue + TTL

你有一个 queue 并且你在失败时多次 queue 消息并且当 ttl 过期时你可以设置一个 dlx.

basic.reject 有多个 queues

失败时你总是basic.reject without requeue并使用dlx将消息发送到下一次重试queue:

test ---> test.retries.1 ---> ... ---> test.retries.N ---> test.z_dead

目前我使用这种方法只重试了 1 次 queue 并且我有一个特殊的 queue 从 dlx 接收某些消息并给我发一封电子邮件。 (就我而言,消息会在几个小时内得到确认)

basic.reject加上重试次数

当您执行 basic.reject without requeue 并使用 dlx 时,您可以检查 dlx 添加的 x-death header 以确定重试次数。

这是在 sneakers 中的做法 - a ruby gem:

---> test (queue)
     |
     | test.retry (exchange)
     |
     ---> test.retry (queue - wait for some time with ttl)
          |
          | test.retry.requeue (exchange)
          |
          ---> test (queue)

最后,您计算通过测试的次数 queue,当您超过重试次数时,您必须确认该消息(可能在某处发布之后,这样您就可以收到错误通知)。