Как подружить monolog с redis в lumen

15 June 2015
#Laravel#Lumen#PHP#Redis

В принципе ничего сложного нет. Данная мини статья рассчитана на начинающих в PHP. Суть статьи больше в том, что бы показать, как переопределять методы.

Итак, понадобилось нам писать логи в redis, с чего начать? А начнём мы с того, что заглянем в папочку /vendor/laravel/lumen-framework/src/ в файл Application.php.

    /**
    * Register container bindings for the application.
    *
    * @return void
    */
    protected function registerLogBindings()
    {
        $this->singleton('Psr\Log\LoggerInterface', function () {
            return new Logger('lumen', [$this->getMonologHandler()]);
        });
    }
    
    /**
    * Get the Monolog handler for the application.
    *
    * @return \Monolog\Handler\AbstractHandler
    */
    protected function getMonologHandler()
    {
        return (new StreamHandler(storage_path('logs/lumen.log'), Logger::DEBUG))
        ->setFormatter(new LineFormatter(null, null, true, true));
    }

В файле видим метод registerLogBindings который в свою очередь вызывает getMonologHandler, он то нам и нужен.

Что ж, для начала наследуем класс Application. Я обычно размещаю такие классы в директории /app/Classes/

    <?php
    
    /**
     * Файл Application.php
     */
    
    namespace app\Classes;
    
    // Наследовать будем конечно же от \Laravel\Lumen\Application
    class Application extends \Laravel\Lumen\Application {
    
        }
    
    }

Теперь переопределим метод getMonologHandler

    <?php
    
    namespace app\Classes;
    
    // Импортируем необходимые пространства имён
    use Monolog\Logger;
    use Monolog\Handler\RedisHandler;
    use Monolog\Formatter\JsonFormatter;
    
    // Наследовать будем конечно же от \Laravel\Lumen\Application
    class Application extends \Laravel\Lumen\Application {
    
        /**
         * Get the Monolog handler for the application.
         *
         * @return \Monolog\Handler\AbstractHandler
         */
        protected function getMonologHandler() {
    
            // Создадим экземпляр класса Predis
            $redis = new \Predis\Client("tcp://localhost:6379");
            
            // Добавим дефолтное имя ключа, по которому будут писаться наши логи
            // Для удобства, дадим возможность изменять это значение в файле .env
            $key = env('MONOLOG_REDIS_KEY', 'logs');
    
            return (new RedisHandler($redis, $key, Logger::DEBUG));
    
        }
    
    }

Осталось только подменить наш класс в файле /bootstrap/app.php

    <?php
    /*
    |--------------------------------------------------------------------------
    | Create The Application
    |--------------------------------------------------------------------------
    |
    | Here we will load the environment and create the application instance
    | that serves as the central piece of this framework. We'll use this
    | application as an "IoC" container and router for this 
    |
    */
    
    // Закомментируем либо удалим
    //$app = new Laravel\Lumen\Application(
    //	realpath(__DIR__.'/../')
    //);
    
    $app = new App\Classes\Application(
    	realpath(__DIR__.'/../')
    );

Если оставить сейчас всё как есть, то в redis будут писаться строковые значения. Но нам не составит труда писать это к примеру в формате json.

    return (new RedisHandler($redis, $key, Logger::DEBUG))->setFormatter(new JsonFormatter());

Что почитать?

Классы и Объекты. Основы.

Пространства имён

Так же смотрите и разбирайте исходники lumen