Node.js NodeJS和RabbitMQ,如何确保处理我的消息
我正在构建一种微服务应用程序,并使用RabbitMQ在我的服务之间进行通信 我有一个nodeJS应用程序,它应该从RabbitMQ接收消息,并在收到特定消息时执行命令。下面是以下代码的作用:Node.js NodeJS和RabbitMQ,如何确保处理我的消息,node.js,rabbitmq,Node.js,Rabbitmq,我正在构建一种微服务应用程序,并使用RabbitMQ在我的服务之间进行通信 我有一个nodeJS应用程序,它应该从RabbitMQ接收消息,并在收到特定消息时执行命令。下面是以下代码的作用: 连接到RabbitMQ 侦听symfony\u消息queue 如果出现由product.created标识的消息,脚本将使用child\u进程中的spawn执行特定命令 我的问题是:有时候,我要“重启”我的脚本。如何确保在重新启动脚本时不在处理事件的中间?如何确保进程不会消耗消息并在生成进程之前停止? 我想
symfony\u消息
queueproduct.created
标识的消息,脚本将使用child\u进程中的spawn
执行特定命令
- 向nodeJS进程发送一个信号,告诉他“处理最后一条消息并停止”。但我怎么能发出这样的信号呢
消息处理成功后,在消息上使用channel.ack(消息)函数不是一种好模式吗?您已将noAck选项设置为true,但可以使用ACK机制确保消息只有在成功处理后才从队列中删除 同样,您可以使用Nack函数故意告诉RabbitMQ消息未被处理,我通常在流程函数error handler(或promise.catch)中这样做
我在将消息写入数据库的服务中使用了类似的机制。我只在消息写入数据库后确认消息。在RabbitMQ中设置死信交换/队列也很有用,这样任何被Nacked的消息都会在那里结束。然后,您可以检查这些消息,看看为什么它们不能被处理(或者在导致问题的错误条件得到解决后自动尝试重新处理)。消息处理成功后,对消息使用channel.ack(消息)功能不是一个好模式吗?您已将noAck选项设置为true,但可以使用ACK机制确保消息只有在成功处理后才从队列中删除 同样,您可以使用Nack函数故意告诉RabbitMQ消息未被处理,我通常在流程函数error handler(或promise.catch)中这样做
我在将消息写入数据库的服务中使用了类似的机制。我只在消息写入数据库后确认消息。在RabbitMQ中设置死信交换/队列也很有用,这样任何被Nacked的消息都会在那里结束。然后,您可以检查这些消息,看看为什么无法处理它们(或者在导致问题的错误条件解决后自动尝试重新处理)。太好了,我刚刚阅读了有关Ack和Nack功能的文档,它完全符合我的需要,谢谢!很酷,还可以查看死信功能,捕捉无法处理的奇怪消息非常有用。你点击一条消息,它就会进入死信队列。您的过程可以继续进行,并且您可以在以后更新您的算法来处理这些消息。您可以给我们一个代码示例吗?当消费者发送Nack时,我无法在发布方处理它…太好了,我只是阅读了关于Ack和Nack功能的文档,它完全符合我的需要,谢谢!很酷,还可以查看死信功能,捕捉无法处理的奇怪消息非常有用。你点击一条消息,它就会进入死信队列。您的过程可以继续进行,并且您可以在以后更新您的算法来处理这些消息。您可以给我们一个代码示例吗?当消费者发送Nack时,我无法在发布服务器端处理它。。。
const amqp = require('amqplib/callback_api')
const { spawn } = require('child_process')
amqp.connect('amqp://guest:guest@127.0.0.1:5672', (err, conn) => {
if (err) {
console.log(err)
return
}
conn.createChannel((err, channel) => {
let q = 'symfony_messages'
channel.assertQueue(q, {
durable: false
})
console.log(" [*] Waiting for messages in %s. To exit press CTRL+C", q);
channel.consume(q, (msg) => {
let event = JSON.parse(msg.content.toString())
if (event.name === 'product.created') {
console.log('Indexing order...')
let cp = spawn('php', [path.join(__dirname, '..', '..', 'bin', 'console'), 'elastic:index:orders', event.payload.product_id])
cp.stdout.on('data', (data) => {
console.log(`stdout: ${data}`);
})
cp.stderr.on('data', (data) => {
console.log(`stderr: ${data}`);
})
cp.on('close', (code) => {
console.log(`child process exited with code ${code}`);
})
}
}, {noAck: true});
})
})