Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to register a Zend\Log Instance in the ServiceManager in ZF2

I am wondering what is the best way to initiate and re-use a logger instance through the ServiceManager in ZF2. Of course I can do a simple method to be used in any class, like:

public function getLogger () {
        $this->logger = new Logger();
        $this->logger->addWriter(new Writer\Stream('/log/cms_errors.log'));
        return $logger;
    }

but I was wondering what is the best way to register a similar structure in the global.php. So far I can

add the following to global.php

'Zend\Log'=>array(
        'timestampFormat' => 'Y-m-d',
        array(
            'writerName'   => 'Stream',
            'writerParams' => array(
                'stream'   => '/log/zend.log',
            ),
            'formatterName' => 'Simple',            
        ),
    ),

If I try invoking it through:

$this->getServiceLocator()->get('Zend\Log')

I get a :

Zend\ServiceManager\ServiceManager::get was unable to fetch or create an instance for Zend\Log
like image 541
Al-Punk Avatar asked Jul 27 '12 11:07

Al-Punk


2 Answers

Add the following data to 'global.php'

'service_manager' => array(
    'factories' => array(
        'Zend\Log' => function ($sm) {
            $log = new Zend\Log\Logger();
            $writer = new Zend\Log\Writer\Stream('./data/logs/logfile');
            $log->addWriter($writer);

            return $log;
        },
    ),
),

And then you'll be able to call

$this->getServiceLocator()->get('Zend\Log')->info('Something...');
like image 113
arturgrigor Avatar answered Nov 06 '22 12:11

arturgrigor


Alternatively, and more elegantly, you could setup a log listener and keep your logger decoupled from your app. The EventManager is a very powerful component and ZF2 is basically an event driven framework now.

In your module.php you could add something like:

// Setup the Zend Logger, pseudocode
$logger = new Logger;
$writer = new Writer;
$logger->addWriter($writer);

// Attach a logging listener for the log event on application level, working code
$events = StaticEventManager::getInstance();
$events->attach('*', 'log', function($event) use ($logger) {
    $target = get_class($event->getTarget());
    $message = $event->getParam('message', 'No message provided');
    $priority = (int) $event->getParam('priority', Logger::INFO);
    $message = sprintf('%s: %s', $target, $message);
    $logger->log($priority, $message);
});

Then from anywhere, e.g. from a Controller, you can do:

$this->getEventManager()->trigger('log', $this, array(
                                                       'priority' => 7, 
                                                       'message' => 'some log message'
                                                      ));
like image 11
markus Avatar answered Nov 06 '22 12:11

markus