我遇到的问题是,在另一个消费者收到消息之前,将大约20封AMQP消息发布到RabbitMQ中的共享队列会被批量延迟。我的应用程序拓扑有三个端点:
我看到的是,所有第二个端点都将“保持”其传出消息,直到没有消息从ssh队列中消耗掉。这可以防止将设备配置及时传送到最终端点。我所观察到的是,一旦所有中间端点消耗了他们的消息,每个配置都会同时进入。
所以我的问题是为什么我会看到这种假脱机行为?我希望我们的消息在它们准备好的那一刻就被发布,并且这种行为不是预期的。
端点1 - 网络设备备份请求的发送方:
EventMachine.add_timer( 0 ) do
YAML::load_file( 'hosts.yaml' ).each do |fqdn,ip|
payload = { :fqdn => fqdn }
exchange.publish( payload.to_json, :routing_key => 'net.svc.ssh' )
end
end
端点2 - ssh节点
mq_queue.subscribe( :ack => false ) do |meta, mq_payload|
payload = JSON.parse( mq_payload)
# SSH stuff happens here
mq_channel.default_exchange.publish( payload.to_json,
:routing_key => 'net.svc.savefile',
)
end
end
端点3 - 将设备配置保存到文件
的节点queue.subscribe( ) do |meta, mq_payload|
payload = JSON.parse( mq_payload )
payload[ "host" ].each do |host,hash|
File.open( File.join('backups', host), "w" ) do |file|
result = hash[ "result" ]
if( result[ "error" ].nil? )
file << result[ "show running-config" ].join( "\n" )
else
file << result[ "error" ]
end
end
end
end
答案 0 :(得分:1)
在我看来,您正在使用默认行为向主题交换发布消息。我假设你的消费者(有多个实例)订阅了一个队列,路由密钥上有一个简单的绑定,即多个消费者将循环播放消息。
或者也许只有一个消费者。
我多年没有使用Ruby了,所以我不熟悉各种库的怪癖,但是在看到消息后,我无法看到消费者对消息的确认。在消费者2上,你似乎已经明确地将auto-ack设置为FALSE,这很好,而在消费者3中你没有设置它,所以也许这意味着auto-ack正在发生。
当我编写一个在另一个队列上发布结果的消费者时,我按此顺序执行操作: