Логирование в PHP приложениях: лучшие практики
Логирование — это не просто запись ошибок в файл. Это системный процесс сбора, хранения и анализа информации о работе приложения. В PHP-разработке грамотно настроенное логирование помогает быстро находить баги, отслеживать аномалии в поведении пользователей и обеспечивать аудит безопасности. В этой статье мы разберем лучшие практики логирования в PHP, начиная от стандартов и заканчивая продвинутыми инструментами.
1. Зачем нужно логирование и основные принципы
Логирование решает несколько ключевых задач:
- Отладка — фиксация состояния приложения в момент ошибки.
- Мониторинг — отслеживание производительности и нагрузки.
- Безопасность — запись подозрительных действий (попытки взлома, несанкционированный доступ).
- Аудит — документирование критических бизнес-операций.
Основные принципы хорошего логирования:
- Не лгите — логи должны отражать реальное состояние системы.
- Структурированность — используйте единый формат (JSON, key=value).
- Уровни важности — разделяйте debug, info, warning, error, critical.
- Никаких секретов — никогда не пишите пароли, токены и персональные данные.
2. Стандарт PSR-3 и интерфейс LoggerInterface
PHP-FIG рекомендует использовать PSR-3 — стандартный интерфейс для библиотек логирования. Он определяет 8 уровней (от debug до emergency) и единый контракт.
Пример реализации с использованием PSR-3:
<?php
use Psr\Log\AbstractLogger;
class SimpleLogger extends AbstractLogger
{
public function log($level, $message, array $context = [])
{
$logEntry = sprintf(
'[%s] %s: %s %s',
date('Y-m-d H:i:s'),
strtoupper($level),
$message,
json_encode($context)
);
file_put_contents('/var/log/app.log', $logEntry . PHP_EOL, FILE_APPEND);
}
}
$logger = new SimpleLogger();
$logger->info('Пользователь зарегистрирован', ['user_id' => 42]);
?>
Использование PSR-3 позволяет легко заменить библиотеку логгера (например, с Monolog на собственную реализацию) без изменения кода приложения.
3. Monolog — мощный инструмент для логирования
Monolog — самая популярная библиотека логирования для PHP (установка через Composer: composer require monolog/monolog). Она поддерживает множество обработчиков (handlers) и форматтеров.
Базовая настройка Monolog
<?php
use Monolog\Logger;
use Monolog\Handler\StreamHandler;
use Monolog\Handler\FirePHPHandler;
use Monolog\Formatter\LineFormatter;
$logger = new Logger('my_app');
// Обработчик для файла
$fileHandler = new StreamHandler(__DIR__ . '/logs/app.log', Logger::WARNING);
$fileHandler->setFormatter(new LineFormatter("[%datetime%] %level_name%: %message% %context%\n"));
$logger->pushHandler($fileHandler);
// Обработчик для браузера (FirePHP)
$logger->pushHandler(new FirePHPHandler());
// Использование
$logger->warning('Недостаточно прав доступа', ['user' => 'guest']);
$logger->error('Ошибка подключения к БД', ['db_host' => 'localhost']);
?>
Продвинутые возможности Monolog
- FingersCrossedHandler — буферизирует логи и записывает только при достижении определенного уровня (экономит место).
- GroupHandler — отправляет логи сразу в несколько каналов (файл + Email + Slack).
- Processors — добавляют контекст (IP-адрес, ID сессии, время выполнения).
Пример с процессором для добавления IP:
<?php
use Monolog\Processor\IntrospectionProcessor;
use Monolog\Processor\WebProcessor;
$logger->pushProcessor(new WebProcessor());
$logger->pushProcessor(new IntrospectionProcessor());
// Теперь каждый лог будет содержать IP и место вызова
$logger->info('Страница загружена');
?>
4. Лучшие практики логирования в продакшене
В боевых условиях логирование требует особого подхода. Вот ключевые рекомендации:
4.1. Выбор правильного уровня
Не засоряйте продакшен debug-логами. Используйте:
- debug — только для разработки и тестирования.
- info — стандартные события (запросы, регистрации).
- warning — потенциальные проблемы (медленные запросы, высокое потребление памяти).
- error — исключения, которые можно обработать (ошибка API, недоступность кэша).
- critical — критичные сбои (отказ БД, потеря данных).
4.2. Ротация и хранение логов
Не давайте логам заполнять диск. Настройте ротацию:
<?php
use Monolog\Handler\RotatingFileHandler;
// Хранить логи за 30 дней
$handler = new RotatingFileHandler(__DIR__ . '/logs/app.log', 30, Logger::INFO);
$logger->pushHandler($handler);
?>
4.3. Безопасность логов
- Никогда не логируйте пароли, токены, номера карт.
- Маскируйте чувствительные данные перед записью:
<?php
$context = ['email' => 'user@example.com', 'password' => '***'];
$logger->info('Попытка входа', $context);
?>
- Используйте отдельные файлы для разных уровней (error.log, security.log).
- Ограничьте права доступа к логам (chmod 640).
4.4. Структурированные логи
Для анализа логов через ELK или Graylog используйте JSON-формат:
Блоги
Рекомендаций по книгам
Читайте также