简体   繁体   中英

custom monolog logging channel in symfony2 command

In this cookbook article , we can see how to use a custom channel in a service. But how can I use a custom login channel in a command ?

I created a symfony2 command to perform something. I would like to use monolog to log things done by my command.

Actually, I want to write log for my command in another file than the logs of the application.

Any custom command that extends ContainerAwareCommand , has access to Symfony's service container. You can define a service that logs in a custom channel in your config.

<services>
    <service id="console.logger" parent="monolog.logger_prototype">
        <argument index="0">mychannel</argument>
    </service>
</services>

You can access your service from the command the following way

$logger = $this->getContainer()->get('console.logger');

This logger will log with channel as "mychannel".

FYI The default logger service logs to channel "app". This can be seen in the file Symfony/Bundle/MonologBundle/Resources/config/monolog.xml . This is also the place where the default logger service is defined.

<services>
    <service id="monolog.logger" parent="monolog.logger_prototype" public="false">
        <argument index="0">app</argument>
    </service>

    <service id="logger" alias="monolog.logger" />

    <service id="monolog.logger_prototype" class="%monolog.logger.class%" abstract="true">
        <argument /><!-- Channel -->
    </service>
</services>

Try this, use the library directly

use Monolog\Logger;
use Monolog\Handler\StreamHandler;

// ...

// create a log channel
$log = new Logger('name');
$log->pushHandler(new StreamHandler('path of log file', Logger::WARNING));

//add the erros to log file

try {
    //do something
} catch(Exception $e) {
    $log->addError($e->getMessage());
}

Maybe this can resolve your problem, add this into your command file.

A similar question were asked and answered here:

How to write logs from one service into separate file?

Thanks

For Symfony 3.3 because of autowire services when you want to log on seperate files follow this approach:

For example let us suppose we need to log on 2 rotating files:

  • exception.log : For exceptions caused in the application.
  • dataFetch.log : For calls to an api tha retrieves the applications data.

The on services.yml put:

monolog:
  channels: ['dataFetch', 'exception']

  handlers:

    dataFetch:
     type: 'rotating_file'
     level: info
     type: stream
     path: 'dataFetch.log'
     max_files: 7
     channels: dataFetch

    exception:
         type: 'rotating_file'
         level: error
         type: stream
         path: 'exception.log'
         max_files: 7
         channels: exception

Now for the exception loger you can inject ad dependency the monolog.logger.exception while for the dataFetch you can dependency inject the monolog.logger.dataFetch .

In most cases, your command extends ContainerAwareCommand (as seen here: http://symfony.com/doc/current/cookbook/console.html#creating-a-basic-command ).

This means that your command has access to Symfony's service container - which is a big bag of all of the services inside Symfony (ie the useful objects). In your case, you need the logger service, which you can get by grabbing it out of the container:

$logger = $this->getContainer()->get('logger');

(reference: http://symfony.com/doc/current/cookbook/console.html#getting-services-from-the-service-container )

Now you can use the logger as normal. If you ever need any other services, just check out the php app/console container:debug command, which lists every single service on the container.

Good luck!

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM