PHP错误处理:die()Vs trigger_error()Vs抛出异常

时间:2011-08-15 08:42:09

标签: error-handling php

关于PHP中的错误处理 - 据我所知,有3种样式:

  1. die()exit()样式:

    $con = mysql_connect("localhost","root","password");
    
    if (!$con) {
     die('Could not connect: ' . mysql_error());
    }
    
  2. throw Exception样式:

     if (!function_exists('curl_init')) {
    
          throw new Exception('need the CURL PHP extension. 
                               Recomplie PHP with curl');
        }
    
  3. trigger_error()样式:

    if(!is_array($config) && isset($config)) {
            trigger_error('Error: config is not an array or is not set', E_USER_ERROR);
        }
    
  4. 现在,在PHP手册中使用了所有三种方法。

    • 我想知道的是我应该选择哪种风格?为什么呢?

    • 这3个是否相互替换&因此可以互换使用?

    稍微OT:是否仅仅是我或者每个人都认为PHP错误处理选项只是太多到它困扰php开发人员的程度?

2 个答案:

答案 0 :(得分:82)

第一个不应该在生产代码中使用,因为它传输与最终用户无关的信息(用户无法对“无法连接到数据库”做任何事情。)

如果您知道在某个关键代码点,您的应用程序可能会失败并且您希望代码在多个调用级别之间恢复,则会抛出异常。

trigger_error()可让您进行细粒度错误报告(通过使用不同级别的错误消息),您可以隐藏最终用户的这些错误(使用set_error_handler()),但仍然可以向您显示在测试期间。

同样trigger_error()可以生成在开发过程中非常重要的非致命消息,可以使用自定义错误处理程序在生产代码中抑制这些消息。您也可能产生致命错误(E_USER_ERROR),但这些错误无法恢复。如果触发其中一个,则程序执行在此时停止。这就是为什么,对于致命错误,应该使用例外。这样,您就可以更好地控制程序的流程:

// Example (pseudo-code for db queries):

$db->query('START TRANSACTION');

try {
    while ($row = gather_data()) {
       $db->query('INSERT INTO `table` (`foo`,`bar`) VALUES(?,?)', ...);
    }
    $db->query('COMMIT');
} catch(Exception $e) {
    $db->query('ROLLBACK');
}

在这里,如果gather_data()只是简单明了(使用E_USER_ERRORdie()),那么以前的INSERT语句就有可能进入你的数据库,即使不是期望,你无法控制下一步会发生什么。

答案 1 :(得分:9)

我通常在开发代码中使用第一种方式进行简单调试。不建议用于生产。最好的方法是抛出一个异常,你可以在程序的其他部分捕获它并进行一些错误处理。

这三种风格并非相互替代。第一个根本不是错误,而只是一种停止脚本并输出一些调试信息以供您手动解析的方法。第二个不是错误本身,但如果你没有捕获它将被转换为错误。最后一个是在PHP引擎中触发一个真正的错误,它将根据PHP环境的配置进行处理(在某些情况下向用户显示,在其他情况下只记录到文件或根本不保存)。