GuzzleHttp异步请求异常

时间:2014-10-28 08:39:54

标签: php guzzle

我无法弄清楚如何从Guzzle future response处理程序中抛出异常。 这是我的代码:

<?php
require 'vendor/autoload.php';

$client = new \GuzzleHttp\Client();

$req = $client->createRequest('GET', 'http://www.google.com', array(
    'future' => true,
));
echo "Sending request\n";
$response = $client->send($req);

try {
    $response->then(function ($data) {
        echo "Response is received\n";
        throw new Exception('Test');
    })->then(function () {
        // success handler
    }, function (Exception $exception) {
        echo "Error handler invoked\n";
        throw $exception;
    });
} catch (Exception $e) {
    echo "Exception catched\n";
}
echo "Finish\n";

在这种情况下永远不会到达catch块。

2 个答案:

答案 0 :(得分:8)

使用异步Guzzle请求时,您正在使用promises。使用then()之外的FutureResponse函数将创建在请求完成时已履行或拒绝的承诺。如果在发送时发生错误,则拒绝承诺,这意味着将调用提供给then函数的第二个回调。请求成功完成后,将解析该请求,并调用提供给then函数的第一个回调。当任何promise函数抛出异常时,异常会在promise内部被捕获并转发到链中的下一个错误处理程序。在您的示例中,如果请求成功,则抛出异常将触发错误回调。在错误回调中抛出异常会将异常转发到promise链中的下一个错误回调,或者默默地吃掉错误(在你的情况下,没有进一步的错误回调来触发)。

Guzzle使用的React Promises库有更多关于promise的解析和拒绝转发的文档:https://github.com/reactphp/promise#how-promise-forwarding-works。这个库的作者正在考虑添加一个done()函数,该函数可以用作实际抛出未处理异常的终端承诺处理程序。

答案 1 :(得分:0)

异步意味着您的脚本不会等待响应从服务器返回,而只是发送请求并继续执行。在这种情况下,脚本在响应返回之前达到其生命周期,因此不会执行任何回调。

在catch之后添加此行以阻止脚本执行,直到响应返回。

$response->getStatusCode(); 

如果您提供有关您希望实现的目标的更多信息,我们可能会为您提供进一步的帮助。