在异常处理程序中抛出异常

时间:2011-10-21 23:01:39

标签: php exception exception-handling error-handling

我有一个带有异常处理程序的脚本。在异常之后脚本退出之前,此异常处理程序会清除几个连接。

我想从这个异常处理程序中重新抛出异常,以便它由PHP自己的最后一个异常处理程序处理,其中错误被写入PHP的错误日志,或者在PHP中配置的默认值。的.ini。

不幸的是,这似乎不太可能,如下所述:

http://www.php.net/manual/en/function.set-exception-handler.php#68712

  

将导致致命错误:抛出没有堆栈帧的异常

还有另一种方法可以将错误压缩到堆栈中,以便PHP在我的异常处理程序清理完成后处理它吗?

5 个答案:

答案 0 :(得分:15)

你不能从异常处理程序中重新抛出,但是,还有其他地方可以。例如,您可以通过将事物封装到自己的类中来解除对处理程序的重新抛出,然后使用__destruct()函数(PHP 5.3,Demo):

<?php

class ExceptionHandler
{
    private $rethrow;
    public function __construct()
    {
        set_exception_handler(array($this, 'handler'));
    }
    public function handler($exception)
    {
        echo  "cleaning up.\n";
        $this->rethrow = $exception;
    }
    public function __destruct()
    {
        if ($this->rethrow) throw $this->rethrow;
    }
}

$handler = new ExceptionHandler;

throw new Exception();

将其放入我的错误日志中:

[29-Oct-2011 xx:32:25] PHP Fatal error: Uncaught exception 'Exception' in /.../test-exception.php:23
Stack trace:
#0 {main}
thrown in /.../test-exception.php on line 23

答案 1 :(得分:8)

只需捕获异常并自行记录消息,然后重新抛出。

try {
    $foo->doSomethingToCauseException();
} catch (Exception $e) {
    error_log($e->getMessage());
    throw $e;
}

如果你冒泡到顶部并且PHP无法处理,则会导致未捕获的异常。

答案 2 :(得分:3)

  

将导致致命错误:抛出没有堆栈帧的异常

此错误意味着您的异常是从不属于脚本的代码中抛出的(据PHP所知)。此类代码的示例包括使用set_exception_handler()设置的自定义异常处理程序以及任何类析构函数方法。除了不从这样的代码中抛出异常,别无选择。

如果您想要PHP本机错误处理,我建议您拨打trigger_error()。如果您没有自定义错误处理程序并且使用了合适的错误类型,它应该记录错误。例如,E_USER_ERROR应该没问题。

答案 3 :(得分:2)

只需将异常重新抛出为RunTimeException,它将保留stacktrace:)

try {
    // bad exception throwing code
} catch (Exception $e) {
    throw new RuntimeException($e->getMessage(), $e->getCode(), $e);
}

答案 4 :(得分:0)

来自http://www.php.net/manual/en/function.set-exception-handler.php#88082 我读: 另一种解决方案是在异常处理程序的开头恢复错误处理程序。 你试过吗?