web-dev-qa-db-ja.com

python / pikaで複数のキューを消費する

複数のキューをサブスクライブし、到着したメッセージを処理するコンシューマーを作成しようとしています。

問題は、最初のキューにすでにデータが存在する場合、最初のキューを消費し、2番目のキューを消費しないことです。ただし、最初のキューが空の場合、次のキューに移動し、両方のキューを同時に消費します。

私は最初にスレッディングを実装しましたが、pikaライブラリーがそれほど複雑ではなく私のためにそれを行うときに、それを避けたいと思います。以下は私のコードです:

import pika

mq_connection = pika.BlockingConnection(pika.ConnectionParameters('x.x.x.x'))
mq_channel = mq_connection.channel()
mq_channel.basic_qos(prefetch_count=1)


def callback(ch, method, properties, body):
    print body
    mq_channel.basic_ack(delivery_tag=method.delivery_tag)

mq_channel.basic_consume(callback, queue='queue1', consumer_tag="ctag1.0")
mq_channel.basic_consume(callback, queue='queue2', consumer_tag="ctag2.0")
mq_channel.start_consuming()
36
user3295878

解決策の1つは、非ブロッキング接続を使用してメッセージを消費することです。

import pika


def callback(channel, method, properties, body):
    print(body)
    channel.basic_ack(delivery_tag=method.delivery_tag)


def on_open(connection):
    connection.channel(on_channel_open)


def on_channel_open(channel):
    channel.basic_consume(callback, queue='queue1')
    channel.basic_consume(callback, queue='queue2')


parameters = pika.URLParameters('amqp://guest:guest@localhost:5672/%2F')
connection = pika.SelectConnection(parameters=parameters,
                                   on_open_callback=on_open)

try:
    connection.ioloop.start()
except KeyboardInterrupt:
    connection.close()

これは複数のキューに接続し、それに応じてメッセージを消費します。

18
ChillarAnand

この問題は、最初の呼び出しがBasic.Consumeを発行し、2番目の呼び出しが発行される前に事前入力されたキューからメッセージをすでに受信している可能性が高いです。 QoSプリフェッチカウントを1に設定すると、RabbitMQが一度に複数のメッセージを送信するのを制限できます。

2
Gavin M. Roy