Как я могу получать полезные сообщения об ошибках в PHP?
Довольно часто я пытаюсь запустить PHP-скрипт и просто получаю пустой экран. Сообщение об ошибке отсутствует; просто пустой экран. Причиной могла быть простая синтаксическая ошибка (неправильная скобка, отсутствие точки с запятой), неудачный вызов функции или что-то еще.
Очень сложно понять, что пошло не так. Я заканчиваю тем, что комментирую код, везде ввожу "эхо" и т.д., пытаясь сузить проблему. Но ведь должен быть способ получше, правда?
Есть ли способ заставить PHP выдавать полезное сообщение об ошибке, как это делает Java?
Ответы
Для синтаксических ошибок необходимо включить отображение ошибок в php.ini. По умолчанию они отключены, потому что вы не хотите, чтобы «клиент» видел сообщения об ошибках. Проверьте эту страницу в документации PHP для получения информации о 2 директивах: error_reporting
и display_errors
. display_errors
вероятно, тот, который вы хотите изменить. Если вы не можете изменить php.ini, вы также можете добавить следующие строки в файл .htaccess:
php_flag display_errors on
php_value error_reporting 2039
Вы можете рассмотреть возможность использования значения E_ALL (как указано Gumbo) для вашей версии PHP, error_reporting
чтобы получить все ошибки. больше информации
3 других элемента: (1) Вы можете проверить файл журнала ошибок, так как он будет содержать все ошибки (если ведение журнала не было отключено). (2) Добавление следующих 2 строк поможет вам отладить ошибки, которые не являются синтаксическими ошибками:
error_reporting(-1);
ini_set('display_errors', 'On');
(3) Другой вариант - использовать редактор, который проверяет наличие ошибок при вводе , например PhpEd . PhpEd также поставляется с отладчиком, который может предоставить более подробную информацию. (Отладчик PhpEd очень похож на xdebug и интегрируется непосредственно в редактор, поэтому вы используете одну программу для всего.)
Ссылка Картмана тоже очень хороша:http://www.ibm.com/developerworks/library/os-debug/
Следующее разрешает все ошибки:
ini_set('display_startup_errors', 1);
ini_set('display_errors', 1);
error_reporting(-1);
Также см. Следующие ссылки
- http://php.net/manual/en/errorfunc.configuration.php#ini.display-errors
- http://php.net/manual/en/errorfunc.configuration.php#ini.display-startup-errors
- http://php.net/manual/en/function.error-reporting.php
Следующий код должен отображать все ошибки:
<?php
// ----------------------------------------------------------------------------------------------------
// - Display Errors
// ----------------------------------------------------------------------------------------------------
ini_set('display_errors', 'On');
ini_set('html_errors', 0);
// ----------------------------------------------------------------------------------------------------
// - Error Reporting
// ----------------------------------------------------------------------------------------------------
error_reporting(-1);
// ----------------------------------------------------------------------------------------------------
// - Shutdown Handler
// ----------------------------------------------------------------------------------------------------
function ShutdownHandler()
{
if(@is_array($error = @error_get_last())) { return(@call_user_func_array('ErrorHandler', $error));
};
return(TRUE);
};
register_shutdown_function('ShutdownHandler');
// ----------------------------------------------------------------------------------------------------
// - Error Handler
// ----------------------------------------------------------------------------------------------------
function ErrorHandler($type, $message, $file, $line)
{
$_ERRORS = Array( 0x0001 => 'E_ERROR', 0x0002 => 'E_WARNING', 0x0004 => 'E_PARSE', 0x0008 => 'E_NOTICE', 0x0010 => 'E_CORE_ERROR', 0x0020 => 'E_CORE_WARNING', 0x0040 => 'E_COMPILE_ERROR', 0x0080 => 'E_COMPILE_WARNING', 0x0100 => 'E_USER_ERROR', 0x0200 => 'E_USER_WARNING', 0x0400 => 'E_USER_NOTICE', 0x0800 => 'E_STRICT', 0x1000 => 'E_RECOVERABLE_ERROR', 0x2000 => 'E_DEPRECATED', 0x4000 => 'E_USER_DEPRECATED' ); if(!@is_string($name = @array_search($type, @array_flip($_ERRORS))))
{
$name = 'E_UNKNOWN'; }; return(print(@sprintf("%s Error in file \xBB%s\xAB at line %d: %s\n", $name, @basename($file), $line, $message))); }; $old_error_handler = set_error_handler("ErrorHandler");
// other php code
?>
Единственный способ создать пустую страницу с этим кодом - это когда у вас есть ошибка в обработчике завершения работы. Я скопировал и вставил это со своей собственной cms, не тестируя, но уверен, что это работает.
Вы можете включить в файл, который хотите отладить, следующие строки:
error_reporting(E_ALL);
ini_set('display_errors', '1');
Это отменяет настройки по умолчанию в php.ini, которые просто заставляют PHP сообщать об ошибках в журнал.
Ошибки и предупреждения обычно появляются в настройках php.ini ....\logs\php_error.log
или ....\logs\apache_error.log
зависят от них.
Также полезные ошибки часто направляются в браузер, но, поскольку они не являются допустимым HTML, они не отображаются.
Итак, "tail -f
"ваши файлы журналов и когда вы получаете пустой экран, используйте пункты меню IEs" view "->" source "для просмотра необработанного вывода.
Конфигурация PHP
2 записи в php.ini определяют вывод ошибок:
- display_errors
- error_reporting
В производстве , display_errors
обычно устанавливается Off
(что это хорошая вещь, потому что ошибка отображения в производственных объектах , как правило , не желательно!).
Однако при разработке его следует установить в значение On
, чтобы отображались ошибки. Проверить !
error_reporting
( E_ALL & ~E_NOTICE & ~E_STRICT & ~E_DEPRECATED
начиная с PHP 5.3) по умолчанию установлено значение (то есть отображается все, кроме уведомлений, строгих стандартов и уведомлений об устаревании). В случае сомнений установите E_ALL
для отображения всех ошибок. Проверить !
ВОУ ВОУ! Без проверки! Я не могу изменить свой php.ini!
Это позор. Обычно общие хосты не позволяют изменять свой файл php.ini, поэтому эта опция, к сожалению, недоступна. Но не бойтесь! У нас есть другие варианты !
Конфигурация времени выполнения
В желаемом скрипте мы можем изменять записи php.ini во время выполнения! Это означает, что он запустится при запуске скрипта! Милая!
error_reporting(E_ALL);
ini_set("display_errors", "On");
Эти две строки будут иметь тот же эффект, что и изменение записей php.ini, как указано выше! Потрясающие!
У меня все еще появляется пустая страница / ошибка 500!
Значит, скрипт даже не запустился! Обычно это происходит при синтаксической ошибке!
С синтаксическими ошибками сценарий даже не попадает во время выполнения. Он не работает во время компиляции , что означает, что он будет использовать значения в php.ini, которые, если вы не изменили их, могут не позволить отображать ошибки.
Журналы ошибок
Кроме того, PHP по умолчанию регистрирует ошибки. На виртуальном хостинге он может находиться в отдельной папке или в той же папке, что и скрипт-нарушитель.
Если у вас есть доступ к php.ini, вы можете найти его под error_logзаписью.
Я всегда использую этот синтаксис в самом начале PHP-скрипта.
ini_set('error_reporting', E_ALL);
ini_set('display_errors', 'On'); //On or Off
Существует действительно полезное расширение под названием « xdebug », которое также сделает ваши отчеты намного лучше.
Для быстрого и практического устранения неполадок я обычно предлагаю здесь SO:
error_reporting(~0); ini_set('display_errors', 1);
быть помещенным в начало сценария, который находится в стадии устранения. Это не идеально, идеальным вариантом является то, что вы также включаете это в php.ini
и регистрируете ошибки в PHP, чтобы выявлять синтаксические ошибки и ошибки запуска.
В описанных здесь настройках отображаются все ошибки, уведомления и предупреждения, в том числе строгие, независимо от версии PHP.
Следующие моменты, которые следует учитывать:
- Установите Xdebug и включите удаленную отладку в своей среде IDE.
Смотрите также:
- Отчеты об ошибках (PHP The Right Way.)
- Предопределенные константы Документы
- error_reporting()Документы
- display_errorsДокументы
Можно зарегистрировать ловушку, чтобы сделать последнюю ошибку или предупреждение видимыми.
function shutdown(){
var_dump(error_get_last());
}
register_shutdown_function('shutdown');
добавление этого кода в начало index.php поможет вам отладить проблемы.
Если вы супер крутые, можете попробовать:
$test_server = $_SERVER['SERVER_NAME'] == "127.0.0.1" || $_SERVER['SERVER_NAME'] == "localhost" || substr($_SERVER['SERVER_NAME'],0,3) == "192";
ini_set('display_errors',$test_server);
error_reporting(E_ALL|E_STRICT);
Это будет отображать ошибки только при локальном запуске. Он также дает вам переменную test_server для использования в других местах, где это необходимо.
Любые ошибки, возникающие до запуска сценария, не будут обнаружены, но для 99% ошибок, которые я делаю, это не проблема.
Вверху страницы выберите параметр
error_reporting(E_ERROR | E_WARNING | E_PARSE);
Это проблема конфигурации загруженной и рабочей среды.
Важно понимать, что на этапе компиляции или синтаксического анализа возникает синтаксическая ошибка или ошибка синтаксического анализа , а это означает, что PHP выйдет из строя еще до того, как у него будет возможность выполнить любой из ваших кодов. Таким образом, если вы изменяете display_errors
конфигурацию PHP во время выполнения (это включает в себя все, от использования ini_set
в вашем коде до использования .htaccess, который является файлом конфигурации времени выполнения), то используются только загруженные по умолчанию параметры конфигурации .
Как всегда избегать WSOD в разработке
Чтобы избежать WSOD вы хотите , чтобы убедиться , что ваш загруженный файл конфигурации имеет display_errors
на и error_reporting
набор для -1
( это эквивалентно E_ALL , поскольку он гарантирует , что все биты включаются независимо от того, какая версия PHP вы работаете ). Не следует жестко кодировать постоянное значение E_ALL, потому что это значение может меняться в разных версиях PHP.
Загруженная конфигурация - это либо ваш загруженный php.ini
файл, либо ваш apache.conf
или httpd.conf
или файл виртуального хоста. Эти файлы читаются только один раз на этапе запуска (например, при первом запуске apache httpd или php-fpm) и заменяются только изменениями конфигурации времени выполнения. Убедитесь, что display_errors = 1
и error_reporting = -1
в загруженном файле конфигурации гарантирует, что вы никогда не увидите WSOD, независимо от синтаксиса или ошибки синтаксического анализа, которые возникают до того, как изменение среды выполнения, например ini_set('display_errors', 1);
или error_reporting(E_ALL);
может произойти.
Как найти загруженные вами (php.ini) файлы конфигурации
Чтобы найти загруженный файл (-ы) конфигурации, просто создайте новый файл PHP только со следующим кодом ...
<?php
phpinfo();
Затем укажите туда свой браузер и просмотрите проанализированные загруженный файл конфигурации и дополнительные файлы .ini , которые обычно находятся вверху вашего файла и phpinfo()
включают абсолютный путь ко всем загруженным файлам конфигурации.
Если вы видите (none)
вместо файла, это означает, что у вас нет php.ini в пути к файлу конфигурации (php.ini) . Таким образом, вы можете скачать стандартный php.ini в комплекте с PHP отсюда и скопировать его в путь к вашему файлу конфигурации как php.ini, а затем убедиться, что у вашего пользователя php достаточно прав для чтения из этого файла. Вам нужно будет перезапустить httpd или php-fpm, чтобы загрузить его. Помните, что это файл php.ini разработки, который поставляется вместе с исходным кодом PHP. Поэтому, пожалуйста, не используйте его в производстве!
Просто не делайте этого на производстве
Это действительно лучший способ избежать WSOD в разработке. Любой, кто предлагает вам поместить ini_set('display_errors', 1);
или error_reporting(E_ALL);
в начало вашего PHP-скрипта или использовать .htaccess, как здесь, не поможет вам избежать WSOD, когда возникает синтаксическая или синтаксическая ошибка (как в вашем случае здесь), если ваш загруженный файл конфигурации был display_errors
выключен.
Многие люди (и стандартные установки PHP) будут использовать производственный ini-файл, который display_errors
по умолчанию отключен, что обычно приводит к тому же разочарованию, которое вы испытали здесь. Поскольку PHP уже отключил его при запуске, затем обнаруживается синтаксическая ошибка или ошибка синтаксического анализа, и ничего не выводится. Вы ожидаете, что вы ini_set('display_errors',1);
наверху вашего PHP-скрипта должны этого избежать, но не имеет значения, не сможет ли PHP проанализировать ваш код, потому что он никогда не достигнет времени выполнения.
Чтобы сохранить это и сделать его комфортным, вы можете отредактировать файл php.ini. Обычно он хранится в /etc/php.ini
или /etc/php/php.ini
, но более локальные php.ini
могут перезаписать его, в зависимости от рекомендаций вашего хостинг-провайдера по настройке. Проверьте phpinfo()
файл Loaded Configuration File
вверху, чтобы узнать, какой из них загружается последним.
Найдите в этом файле display_errors. Должно быть всего 3 экземпляра, из которых 2 являются комментариями.
Измените строку без комментариев на:
display_errors = stdout
Не знаю, поможет ли это, но вот часть моего стандартного файла конфигурации для проектов PHP. Я стараюсь не слишком сильно зависеть от конфигураций apache даже на моем собственном сервере.
У меня никогда не было проблемы с исчезающей ошибкой, поэтому, возможно, что-то здесь подскажет вам.
Отредактировано для отображения APPLICATON_LIVE
/*
APPLICATION_LIVE will be used in process to tell if we are in a development or production environment. It's generally set as early as possible (often the first code to run), before any config, url routing, etc.
*/
if ( preg_match( "%^(www.)?livedomain.com$%", $_SERVER["HTTP_HOST"]) ) {
define('APPLICATION_LIVE', true);
} elseif ( preg_match( "%^(www.)?devdomain.net$%", $_SERVER["HTTP_HOST"]) ) {
define('APPLICATION_LIVE', false);
} else {
die("INVALID HOST REQUEST (".$_SERVER["HTTP_HOST"].")");
// Log or take other appropriate action.
}
/*
--------------------------------------------------------------------
DEFAULT ERROR HANDLING
--------------------------------------------------------------------
Default error logging. Some of these may be changed later based on APPLICATION_LIVE.
*/
error_reporting(E_ALL & ~E_STRICT);
ini_set ( "display_errors", "0");
ini_set ( "display_startup_errors", "0");
ini_set ( "log_errors", 1);
ini_set ( "log_errors_max_len", 0);
ini_set ( "error_log", APPLICATION_ROOT."logs/php_error_log.txt");
ini_set ( "display_errors", "0");
ini_set ( "display_startup_errors", "0");
if ( ! APPLICATION_LIVE ) {
// A few changes to error handling for development.
// We will want errors to be visible during development.
ini_set ( "display_errors", "1");
ini_set ( "display_startup_errors", "1");
ini_set ( "html_errors", "1");
ini_set ( "docref_root", "http://www.php.net/");
ini_set ( "error_prepend_string", "<div style='color:red; font-family:verdana; border:1px solid red; padding:5px;'>");
ini_set ( "error_append_string", "</div>");
}
error_reporting(E_ALL | E_STRICT);
ini_set('display_errors', 1);
ini_set('html_errors', 1);
Кроме того, вы можете получить более подробную информацию с помощью xdebug .
Я рекомендую Nette Tracy для лучшей визуализации ошибок и исключений в PHP:
ini_set('display_errors', 1);
ini_set('display_startup_errors', 1);
error_reporting(E_ALL);
error_reporting(E_ALL | E_STRICT);
И включить отображение ошибок в php.ini
Вы можете зарегистрировать свой собственный обработчик ошибок на PHP. Например, выгрузка всех ошибок в файл может помочь вам в этих непонятных случаях. Обратите внимание, что ваша функция будет вызываться независимо от того, какой у вас текущий error_reporting . Очень простой пример:
function dump_error_to_file($errno, $errstr) {
file_put_contents('/tmp/php-errors', date('Y-m-d H:i:s - ') . $errstr, FILE_APPEND);
}
set_error_handler('dump_error_to_file');
Две ключевые строки, которые вам понадобятся для извлечения полезных ошибок из PHP:
ini_set('display_errors',1);
error_reporting(E_ALL);
Как указывали другие участники, они по умолчанию отключены по соображениям безопасности. В качестве полезного совета - когда вы настраиваете свой сайт, удобно переключиться на разные среды, чтобы эти ошибки были включены по умолчанию в вашей локальной среде и среде разработки. Этого можно достичь с помощью следующего кода (в идеале в вашем index.php или файле конфигурации, чтобы он был активен с самого начала):
switch($_SERVER['SERVER_NAME'])
{
// local
case 'yourdomain.dev':
// dev
case 'dev.yourdomain.com':
ini_set('display_errors',1);
error_reporting(E_ALL);
break;
//live
case 'yourdomain.com':
//...
break;
}
FirePHP также может быть полезен.
откройте свой php.ini, убедитесь, что он установлен на:
display_errors = On
перезапустите ваш сервер.
Вы также можете попробовать PHPStorm в качестве редактора кода. Он обнаружит множество ошибок PHP и других синтаксических ошибок прямо во время ввода текста в редакторе.
если вы пользователь ubuntu, перейдите в свой терминал и запустите эту команду
sudo tail -50f /var/log/apache2/error.log
где будет отображено 50 последних ошибок. Для error.log
apache2 существует файл ошибок, в котором регистрируются все ошибки.
Чтобы включить полный отчет об ошибках, добавьте это в свой скрипт:
error_reporting(E_ALL);
Это вызывает появление даже минимальных предупреждений. И на всякий случай:
ini_set('display_errors', '1');
Заставит отображение ошибок. Это должно быть отключено на производственных серверах, но не при разработке.
«ОШИБКИ» - это самая полезная вещь для разработчиков, чтобы они знали свои ошибки и исправляли их, чтобы система работала идеально.
PHP предоставляет некоторые из лучших способов узнать разработчикам, почему и где их фрагмент кода получает ошибки, поэтому, зная об этих ошибках, разработчики могут улучшить свой код во многих отношениях.
Лучшие способы написать следующие две строки в верхней части скрипта, чтобы получать все сообщения об ошибках:
error_reporting(E_ALL);
ini_set("display_errors", 1);
Другой способ использовать инструменты отладчика, такие как xdebug, в вашей среде IDE.
Вы можете включить полную отчетность об ошибках (включая уведомления и строгие сообщения). Некоторым это кажется слишком многословным, но попробовать стоит. Набор error_reporting
для E_ALL | E_STRICT
вашей php.ini.
error_reporting = E_ALL | E_STRICT
E_STRICT
уведомит вас об устаревших функциях и даст рекомендации по лучшим методам выполнения определенных задач.
Если вам не нужны уведомления, но вы считаете полезными другие типы сообщений, попробуйте исключить уведомления:
error_reporting = (E_ALL | E_STRICT) & ~E_NOTICE
Также убедитесь, что display_errors
он включен в php.ini. Если ваша версия PHP старше 5.2.4, установите для нее значение On
:
display_errors = "On"
Если ваша версия 5.2.4 или новее, используйте:
display_errors = "stderr"
Помимо error_reporting и настройки display_errors ini, вы можете получать ошибки SYNTAX из файлов журнала вашего веб-сервера. Когда я разрабатываю PHP, я загружаю журналы веб-сервера моей системы разработки в свой редактор. Когда я тестирую страницу и получаю пустой экран, файл журнала устаревает, и мой редактор спрашивает, хочу ли я его перезагрузить. Когда я это делаю, я перехожу вниз и обнаруживаю синтаксическую ошибку. Например:
[Sun Apr 19 19:09:11 2009] [error] [client 127.0.0.1] PHP Parse error: syntax error, unexpected T_ENCAPSED_AND_WHITESPACE, expecting T_STRING or T_VARIABLE or T_NUM_STRING in D:\\webroot\\test\\test.php on line 9
Для тех, кто использует nginx и имеет белый экран даже для файла с расширением <?php echo 123;
. В моем случае у меня не было этой обязательной опции для PHP в файле конфигурации nginx:
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
Этой опции не было в файле fastcgi_params, поэтому PHP не работал и в журналах не было ошибок.