Написание метода подписки RabbitMQ в переполнении стека

У меня есть функция, как определено ниже:

public function subscribe($someQueue)
{
$callback = function($msg){
return $msg->body;
};
$this->channel->basic_consume( $someQueue, '', FALSE, TRUE, FALSE, FALSE, $callback);
while(count($this->channel->callbacks)) {
$this->channel->wait();
}
}

Я использую следующую функцию:

Примечание: следующие строки находятся в другом файле класса, следовательно, создается объект класса, который содержит вышеуказанную функцию.

$objRMQ = new RabbitMQ();
$msgBody = $objRMQ->subscribe("someQueue");
echo "message body returned from someMethod: ".$msgBody;

По сути, я хочу вернуть тело каждого сообщения в функцию вызывающей стороны, которая публикуется в очереди.

Токовый выход:

message body returned from subscribe: NULL

Ожидаемый результат:

holla, this is your message from queue

1

Решение

Поскольку этот вопрос старый, но все еще без ответа, я дам краткое объяснение. Вы, наверное, уже разобрались с ответом, но это может помочь кому-то еще в будущем.

Ключевой концепцией здесь является «асинхронное выполнение».

Когда вы подписываетесь на канал, используя basic_consume метод, вы не просите, чтобы колбэк был выполнен один раз, немедленно, но чтобы он выполнялся, когда сообщение становится доступным, а затем каждый раз, когда другое сообщение доступно.

В случае AMQPLib вы ожидаете новых сообщений, повторно вызывая wait() Способ; то есть здесь:

while(count($this->channel->callbacks)) {
$this->channel->wait();
}

Если подумать об этом, в вашем коде есть две ошибки:

  • Линия return $msg->body некуда возвращаться в. Призыв произойдет где-то глубоко в реализации wait() метод, и вы не получите вывод из $this->channel->wait(), так что не могу ничего сделать с этим возвращаемым значением.
  • С другой стороны, когда вы звоните $objRMQ->subscribe("someQueue") от вашего другого класса вы ожидаете, что он что-то вернет, но эта функция не имеет return заявление. Единственный return утверждение находится внутри анонимной функции, которую вы передали basic_consume,

Решение в основном сделать все ваша обработка сообщения — echo $msg->bodyили какую-либо реальную обработку вы хотите сделать — внутри обратного вызова. Если вы действительно хотите собирать данные при поступлении сообщений, вы можете сохранить их в некоторой переменной, доступной вне функции обратного вызова, но помните, что в какой-то момент вам нужно будет выйти из wait() цикл, чтобы сделать что-нибудь с этими данными.

0

Другие решения

Других решений пока нет …

По вопросам рекламы [email protected]