2011-09-13 346 views
1

我有一個RabbitMQ的特定用例,我想澄清一些事情並徵求建議。RabbitMQ(和node.js)中的異步確認

考慮這種情況:

1 - 我發佈兩條消息,是要執行的任務:messageA然後messageB

2 - 我的消費者得到messageA,執行包含在該消息中的任務,但當任務正在運行時,服務器崩潰

我的問題是:當服務器重新啓動時,messageA是否會被重新排序,並且會在messageB(與崩潰之前的順序相同)之前重新排序?

據我所知,如果服務器崩潰,messageA將會丟失,因爲我的客戶在收到消息時已默認承認它。

所以我的想法是單獨使用和確認消息:先消耗,運行任務,然後在任務成功執行後確認消息。

您是否看到這種方法存在問題?你會建議我做其他事嗎?

回答

0

在服務器崩潰後,在無應答模式下(見http://www.rabbitmq.com/amqp-0-9-1-reference.html#domain.no-ack)消費的消息不會被重新發送,因爲服務器在交付時完全忘記了這些消息。消費者在交付後對這些消息負責。

只有在成功完成任務後才確認消息是您場景中的正確方法。如果您希望消息在代理崩潰後生存,那麼您還必須確保隊列是持久的,並且消息是持久發佈的(交付模式2),並且發佈者確認或事務用於確保消息寫入磁盤。

如果broker在處理messageA時崩潰,那麼消息順序將被保留。如果消費者而不是經紀人崩潰,那麼消息順序將被顛倒。

1

的RabbitMQ不保留消息的順序重新排隊:

在大多數情況下,是的。假設發佈商在相同頻道上發佈消息M1,M2,M3 和M4(按該順序)並且使用相同的路由 信息。如果這些消息被路由到一個隊列,那麼它們將以它們發佈的相同順序結束。在隊列中消費 將產生M1,M2,M3,然後M4。

但是,只有在沒有重新排序的情況下才能保證訂單。如果消費者在確認消息之前關閉了頻道 ,則消息將被隱含地重新排序。例如,如果消費者收到M1,則 不能確認並關閉該頻道,則下一個消費者將 以M2,M3,M4,M1的順序接收消息。如果消費者調用basic.recover {requeue = true},消息也可以是 。 關於此問題的常見問題至少有一次在更多的 細節中談到此。

RabbitMQ FAQ

這是可以做到,但RabbitMQ的不這樣做,它會自動您需要在父消息包裹孩子的消息自行管理的生命週期。然後,您將擁有管理父消息並處理回滾(如果消息1成功但消息2失敗)的代碼。希望有幫助..

最好的問候