doushou3814 2011-05-12 15:08 采纳率: 100%
浏览 127
已采纳

尝试在PHP中使用全局异常处理程序以统一的方式处理各种顶级异常

Please consider the following code:

<?php

class MyException extends Exception {}

function global_exception_handler($exception)
{
    switch (get_class($exception)) {
    case 'MyException':
        print "I am being handled in a unified way.
";
        break;
    default:
        $backtrace = debug_backtrace();
        $exception_trace_object = $backtrace[0]['args'][0];
        var_dump($exception_trace_object);
        print "----
";
        $reflected_exception_trace_object = new ReflectionObject($exception_trace_object);
        $reflected_trace_property = $reflected_exception_trace_object->getProperty('trace');
        $reflected_trace_property->setAccessible(true);
        var_dump($reflected_trace_property);
        print "----
";

        // NOT WORKING, I STUCK HERE.
        var_dump($reflected_trace_property->getValue($reflected_trace_property));

        throw $exception;
    }
}

set_exception_handler('global_exception_handler');

function function1()
{
    function2();
}

function function2()
{
    function3();
}

function function3()
{
    throw new Exception();
}

function1();

?>

What I'm trying to do is handling various types of exceptions in a unified way across various files by simply setting up a global exception handler without having to write any boilerplate code (except the header and footer includes which are present in every file).

The problem is that when the thrown exception type is not handled by the global exception handler and I want to rethrow the exception, the stack trace gets lost which is a limitation of using set_exception_handler().

I can retrieve the stack trace by using debug_backtrace() but I cannot access its relevant private members to be able to print it appropriately.

This is what the above script produces:

object(Exception)#1 (7) {
  ["message":protected]=>
  string(0) ""
  ["string":"Exception":private]=>
  string(0) ""
  ["code":protected]=>
  int(0)
  ["file":protected]=>
  string(28) "/home/laci/download/test.php"
  ["line":protected]=>
  int(42)
  ["trace":"Exception":private]=>
  array(3) {
    [0]=>
    array(4) {
      ["file"]=>
      string(28) "/home/laci/download/test.php"
      ["line"]=>
      int(37)
      ["function"]=>
      string(9) "function3"
      ["args"]=>
      array(0) {
      }
    }
    [1]=>
    array(4) {
      ["file"]=>
      string(28) "/home/laci/download/test.php"
      ["line"]=>
      int(32)
      ["function"]=>
      string(9) "function2"
      ["args"]=>
      array(0) {
      }
    }
    [2]=>
    array(4) {
      ["file"]=>
      string(28) "/home/laci/download/test.php"
      ["line"]=>
      int(45)
      ["function"]=>
      string(9) "function1"
      ["args"]=>
      array(0) {
      }
    }
  }
  ["previous":"Exception":private]=>
  NULL
}
----
object(ReflectionProperty)#3 (2) {
  ["name"]=>
  string(5) "trace"
  ["class"]=>
  string(9) "Exception"
}
----
NULL

Fatal error: Exception thrown without a stack frame in Unknown on line 0

Thanks in advance!

  • 写回答

1条回答 默认 最新

  • dsc862009 2011-05-12 15:24
    关注

    Check the comments on http://php.net/manual/de/function.set-exception-handler.php there are several similar issues and solutions there. For your code I see two possible solutions:

    Change your code into

    function global_exception_handler($exception = NULL)
    

    or add a description to

    throw new Exception('Testing here...');
    
    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论

报告相同问题?

悬赏问题

  • ¥15 kafka 分区副本增加会导致消息丢失或者不可用吗?
  • ¥15 微信公众号自制会员卡没有收款渠道啊
  • ¥15 stable diffusion
  • ¥100 Jenkins自动化部署—悬赏100元
  • ¥15 关于#python#的问题:求帮写python代码
  • ¥20 MATLAB画图图形出现上下震荡的线条
  • ¥15 关于#windows#的问题:怎么用WIN 11系统的电脑 克隆WIN NT3.51-4.0系统的硬盘
  • ¥15 perl MISA分析p3_in脚本出错
  • ¥15 k8s部署jupyterlab,jupyterlab保存不了文件
  • ¥15 ubuntu虚拟机打包apk错误