如何在ReactPHP Browser的Promise中链式处理多种异常类型?
ReactPHP Promise 多异常类型优雅处理方案
ReactPHP 原生 Promise 的 then/otherwise 方法不支持直接链式添加多个失败处理函数并自动匹配异常类型,但可以通过自定义异常匹配逻辑+Promise链式调用实现类似 try-catch 多类型捕获的效果。
方案一:自定义catchType工具函数(推荐)
封装一个工具函数,专门用来匹配指定类型的异常,实现语义化的多异常处理:
/** * 创建针对特定异常类型的处理函数 * @param string $type 目标异常类名(支持继承关系) * @param callable $handler 匹配成功后的处理逻辑 * @return callable */ function catchType(string $type, callable $handler): callable { return function (\Throwable $e) use ($type, $handler) { if ($e instanceof $type) { return $handler($e); } // 非目标类型,重新抛出异常交给后续处理 throw $e; }; }
使用示例:
use Psr\Http\Message\ResponseInterface; use React\Http\Message\ResponseException; $browser->post($uri, $headers, $body) ->then(function (ResponseInterface $response) { // 处理正常响应 var_dump((string)$response->getBody()); }) // 优先处理ResponseException类型异常 ->otherwise(catchType(ResponseException::class, function (ResponseException $e) { echo '响应异常: 状态码' . $e->getResponse()->getStatusCode() . PHP_EOL; })) // 处理其他所有未匹配的异常/错误 ->otherwise(function (\Throwable $e) { echo '系统错误: ' . $e->getMessage() . PHP_EOL; });
原理:otherwise会接收前序未被处理的异常,若当前catchType不匹配目标类型,则重新抛出异常,流转到下一个otherwise处理,完全模拟try-catch的顺序匹配逻辑。
方案二:链式then手动分发异常
利用Promise链式调用的特性,在每个then的失败回调中处理特定异常,不匹配则抛出给后续处理:
use Psr\Http\Message\ResponseInterface; use React\Http\Message\ResponseException; $browser->post($uri, $headers, $body) ->then( function (ResponseInterface $response) { // 处理正常响应 var_dump((string)$response->getBody()); }, function (\Throwable $e) { if ($e instanceof ResponseException) { // 处理ResponseException echo '响应异常: 状态码' . $e->getResponse()->getStatusCode() . PHP_EOL; } else { // 非目标类型,抛出给下一个then处理 throw $e; } } ) ->then(null, function (\Throwable $e) { // 处理其他所有异常/错误 echo '系统错误: ' . $e->getMessage() . PHP_EOL; });
注意事项
- 优先使用
\Throwable代替\Exception,覆盖PHP7+的错误类型(如致命错误、解析错误等) - 异常处理顺序需遵循从具体到通用,先捕获子类异常,再捕获父类/通用异常,避免被提前拦截
内容的提问来源于stack exchange,提问作者Xavi Montero
相关产品推荐
相关产品推荐

