Comment enregistrer une instance Zend\Log dans le ServiceManager dans ZF2
-
12-12-2019 - |
Question
Je me demande quelle est la meilleure façon de lancer et de réutiliser une instance d'enregistreur via ServiceManager dans ZF2.Bien sûr, je peux utiliser une méthode simple à utiliser dans n'importe quelle classe, comme :
public function getLogger () {
$this->logger = new Logger();
$this->logger->addWriter(new Writer\Stream('/log/cms_errors.log'));
return $logger;
}
mais je me demandais quelle est la meilleure façon d'enregistrer une structure similaire dans global.php.Jusqu'à présent, je peux
ajoutez ce qui suit à global.php
'Zend\Log'=>array(
'timestampFormat' => 'Y-m-d',
array(
'writerName' => 'Stream',
'writerParams' => array(
'stream' => '/log/zend.log',
),
'formatterName' => 'Simple',
),
),
Si j'essaie de l'invoquer via :
$this->getServiceLocator()->get('Zend\Log')
J'ai un :
Zend\ServiceManager\ServiceManager::get was unable to fetch or create an instance for Zend\Log
La solution
Ajoutez les données suivantes à '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;
},
),
),
Et puis vous pourrez appeler
$this->getServiceLocator()->get('Zend\Log')->info('Something...');
Autres conseils
Alternativement, et de manière plus élégante, vous pouvez configurer un écouteur de journal et garder votre enregistreur découplé de votre application.Le EventManager
est un composant très puissant et ZF2 est désormais essentiellement un framework piloté par les événements.
Dans ton module.php
tu pourrais ajouter quelque chose comme :
// 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);
});
Puis de n'importe où, par ex.depuis un contrôleur, vous pouvez faire :
$this->getEventManager()->trigger('log', $this, array(
'priority' => 7,
'message' => 'some log message'
));
peut-être utiliser l'usine Abstract Logger pour la configuration au lieu de l'usine normale
return array(
'log' => array(
'Log\App' => array(
'writers' => array(
array(
'name' => 'stream',
'priority' => 1000,
'options' => array(
'stream' => 'data/logs/app.log',
),
),
),
),
),
);
S'il vous plaît essayez à nouveau à l'aide du chemin absolu \
$writer = new \Zend\Log\Writer\Stream('log.log');
$logger = new \Zend\Log\Logger($writer);
J'ai créé un objet Writer de base de données par défaut dans mon bootstrap et l'inscrit dans le servicanager.
public function onBootstrap(MvcEvent $e)
{
...
$serviceManager = $e->getApplication()->getServiceManager();
$dbAdapter = $serviceManager->get('Zend\Db\Adapter\Adapter');
$writer = new \Zend\Log\Writer\Db($dbAdapter, 'log_database_table');
$logger = new \Zend\Log\Logger();
$logger->addWriter($writer);
// this is optional but nice to have
\Zend\Log\Logger::registerErrorHandler($logger);
$serviceManager->setService('Zend\Log', $logger);
}
L'abstractController est une instance de "ServiceLocatorawareInterface".Donc, je peux juste appeler mon contrôleur
public function indexAction()
{
...
$this->getServiceLocator()->get('Zend\Log')->info('this is a test log message');
...
}