【问题标题】:RabbitMQ subscriber sending message back onto RabbitMQ queue?RabbitMQ 订阅者将消息发送回 RabbitMQ 队列?
【发布时间】:2016-06-19 07:34:58
【问题描述】:

感谢您对此的看法。

我有一个订阅 RabbitMQ 队列的节点应用程序。当它收到一条消息时,它会检查它是否有某些内容,然后将其保存到数据库中。

但是,如果消息缺少某些信息或尚未满足某些其他条件,我希望订阅者将消息发布回 RabbitMQ 队列。

我从逻辑上理解这只是连接到队列并发布消息,但它真的这么简单还是这是一种不好的做法或潜在的危险?

感谢您的帮助。

【问题讨论】:

  • 当消息丢失某些东西时,然后发布到从它接收消息的同一个队列中?如果是这样,您可以将autoack 设置为false,除非您给予确认,否则该消息将从队列中删除。然后如果消息缺少某些东西,则没有确认,并且该消息将保留在队列中而不会被删除。如果消息是goo,给这个队列ack,然后这个消息将从队列中删除。
  • @zangw 是发布到它从中获取消息的同一个队列。 (这很难解释,但消息中有一个时间元素,所以它可能在 5 分钟内而不是现在有效)。

标签: node.js rabbitmq message-queue


【解决方案1】:

正如我在评论中指出的,当您创建与队列的连接并设置autoAck = true 以启用消息确认时。队列中的消息将被删除,直到收到确认。

当接收到的消息满足要求时,向该队列发送ack消息,该消息将从队列中删除。否则,没有ack消息发送到队列中,该消息将留在队列中。

正如你在评论中提到的,验证过程可能需要5分钟,只需将发送确认消息设置为验证函数的回调函数即可。

【讨论】:

    【解决方案2】:

    在您的问题中,您描述了何时可能无法处理消息的两个标准:

    1. 如果邮件缺少某些信息或
    2. 其他一些标准尚未满足

    其中的第一个似乎是消息的问题,重新排队有问题的消息似乎没有多大意义。适当的操作是记录错误并删除消息(或调用应用程序包含的任何错误处理逻辑)。

    其中第二个相当模糊,但就本答案而言,我们将假设问题不在于消息,而在于系统中的某些其他组件(例如,可能是网络连接问题)。在这种情况下,消费应用程序可以发送一个Nack (negative acknowldegement),它可以选择将消息重新排队。

    请记住,在第二种情况下,必须关闭消费者,直到错误情况解决,否则消息将被重新传递并无限地错误处理,直到系统备份,从而浪费资源无法处理的消息。

    为什么要使用 nack 而不是简单地重新发布?
    这将在邮件上设置“重新发送”标志,以便您知道它已经发送过一次。还有other options 用于处理不良消息。

    【讨论】: