【发布时间】:2017-01-13 06:53:46
【问题描述】:
我正在共享主机中的站点上工作。我无权访问 PHP ini 文件或 PHP ini_set 函数,也无法使用 php_flag 或 php_value 指令。
我正在使用set_error_handler 函数记录大多数错误,并尝试使用register_shutdown_function 记录致命错误。我在这里尝试了几种捕获致命错误的解决方案:How do I catch a PHP Fatal Error
.我可以成功地使用那里的解决方案在屏幕上显示错误或打开自定义错误页面,并记录非致命错误,但我似乎无法记录致命错误。
这是我尝试的最简单版本:
function errorHandler($num, $str, $file, $line) {
$now = strftime("%B %d, %Y at %I:%M %p", time());
$text = "{$now} → error {$num} in {$file}, line {$line}: {$str}\n";
$errorlog = "my_path/my_log";
$new = file_exists($errorlog) ? false : true;
if($handle = fopen($errorlog, 'a')) {
fwrite($handle, $text);
fclose($handle);
if($new) { chmod($errorlog, 0755); }
} else {
print("Could not open log file for writing"); //I'm using this to test
}
}
function fatalHandler() {
$error = error_get_last();
if($error) {
errorHandler($error["type"], $error["message"], $error["file"], $error["line"]);
}
}
set_error_handler("errorHandler");
register_shutdown_function("fatalHandler");
当我使用非致命错误(例如echo $undefined_variable)对此进行测试时,它可以正常工作并且错误会被正确记录。但是,如果我使用致命错误进行测试,例如undefined_function(),它不会记录任何内容并打印“无法打开日志文件”。如果我在两个错误都存在的情况下进行测试,它会记录非致命错误,但不会记录致命错误。
您的问题已被确定为可能与另一个问题重复。如果那里的答案不能解决您的问题,请编辑以详细解释您问题中独特的部分。
@Vic Seedoubleyew -嗯,最明显的是你提到的问题中提到的警告failed to open stream: ...etc 与我的情况无关。那个警告从未发生过。测试消息:“could not open log file for writing”是我自己的消息,我写给自己给自己,所以我有一些证据证明if语句是正在处理。我编造了那个信息。在我的问题中非常清楚地指出,该信息是我自己制作的。任何遇到我遇到的问题的人都不会收到failed to open stream...etc 的消息,因此解决他们从未收到的消息的问题不会帮助他们。我认为这一切的重点是真正帮助像我这样的傻瓜。
标题:“为什么fopen 在注册关闭函数中失败”不是我的标题。那是别人的编辑。我的问题是为什么我不能写入register_shutdown_function 中的日志。我不知道fopen 是失败了还是有其他问题。我试图从该功能中注销某些内容,但它不起作用。从问题中删除既定目标(退出功能),并添加其他人的评估“为什么fopen 失败”,实际上对于任何来到这里寻求解决我遇到的情况的人来说,它的用处要小得多。如果已经存在一个关于在关闭函数中写入文件的问题,我会找到它。 “为什么fopen 失败”太具体,无法在不知道为什么无法写入函数中的文件的人的搜索中有用。
我不想说任何关于编辑的事情,但既然你要我解释,我就解释一下。我意识到每个人都可能因编辑而获得积分,但请花一点时间考虑一下您的编辑对问题对遇到我遇到的情况的人的有用性的影响。
【问题讨论】:
-
您无法记录在错误处理程序注册之前发生的致命错误。所以请确保它首先运行,在单独的文件中执行此操作也是一个好主意。
-
@ArtisticPhoenix:错误处理程序位于会话文件中,该文件包含在每个页面上第一件事。如果我要求错误处理程序打印或显示错误但不记录它,它怎么会打印或显示错误? 编辑:如果您选择对问题投反对票,请告诉我原因,以便我从中学习。谢谢。
-
如果你不调用函数而是在
fatalHandler()本身中进行所有日志记录,它是否有效? -
@RiggsFolly 感谢您的建议。我尝试它在
fatalHandler()中进行所有日志记录并且不调用函数,但它仍然打印我的测试语句“无法打开..”,但它实际上在屏幕上打印它两次,如如果致命处理程序自动调用errorHandler()?
标签: php error-handling fatal-error