我知道您可以使用 将消息直接发送到队列channel.sendToQueue
,这会产生任务和工作人员的情况,其中只有一个消费者将处理每个任务。
我也知道您可以使用channel.publish
基于主题的交换,并且消息将根据路由键路由到队列。不过,据我了解,这将始终广播给任何匹配队列上的所有订阅者。
我基本上想使用基于主题的交换,但每个任务只有一个消费者处理。我已经阅读了文档,但我没有看到这样做的方法。
我的用例:
我在多个位置设置了微服务实例。可能有两个在加利福尼亚,三个在伦敦,一个在新加坡,等等。创建任务时,唯一重要的是它由给定位置的一个实例处理。
当然,我可以创建数百个名为“usa-90210”、“uk-ec1a”等的队列。看起来使用主题会更干净。考虑到使用通配符的能力,它也会更加灵活。
如果这不是 RabbitMQ 的功能,我也愿意接受其他想法或想法。
更新
根据 istepaniuk 的建议,我尝试创建两个工作人员,每个工作人员将自己的队列绑定到交换:
const connectionA = await amqplib.connect('amqp://guest:guest@127.0.0.1:5672');
const channelA = await connectionA.createChannel();
channelA.assertExchange('test_exchange', 'topic', { durable: false });
await channelA.assertQueue('test_queue_a', { exclusive: true });
channelA.bindQueue('test_queue_a', 'test_exchange', 'usa.*');
await channelA.consume('test_queue_a', () => { console.log('worker a'); }, { noAck: true });
const connectionB = await amqplib.connect('amqp://guest:guest@127.0.0.1:5672');
const channelB = await connectionB.createChannel();
channelB.assertExchange('test_exchange', 'topic', { durable: false });
await channelB.assertQueue('test_queue_b', { exclusive: true });
channelB.bindQueue('test_queue_b', 'test_exchange', 'usa.*');
await channelB.consume('test_queue_b', () => { console.log('worker b'); }, { noAck: true });
const pubConnection = await amqplib.connect('amqp://guest:guest@127.0.0.1:5672');
const pubChannel = await pubConnection.createChannel();
pubChannel.assertExchange('test_exchange', 'topic', { durable: false });
pubChannel.publish('test_exchange', 'usa.90210', Buffer.from(''));
不幸的是,两个消费者仍在接收消息。
worker a
worker b