Would it be possible to get a full example of how is it possible to configure Monolog to store its logs into MongoDB using Symfony 2.6 and Doctrine 2?
Asked
Active
Viewed 4,131 times
1 Answers
8
Full configuration
/app/parameters.yml
mongodb_server: "mongodb://localhost:27017"
mongodb_username: "vagrant"
mongodb_password: "password"
mongodb_database: "testdb"
/app/config.yml
# Doctrine2 MongoDB Bundle
# http://symfony.com/doc/current/bundles/DoctrineMongoDBBundle/index.html
doctrine_mongodb:
default_database: %mongodb_database%
connections:
default:
server: %mongodb_server%
options:
password: %mongodb_password%
username: %mongodb_username%
db: %mongodb_database%
connect: true
log:
server: %mongodb_server%
options:
password: %mongodb_password%
username: %mongodb_username%
db: %mongodb_database%
connect: true
document_managers:
default:
auto_mapping: true
log:
auto_mapping: false
logging: false
/app/services.yml
mongolog:
class: Doctrine\MongoDB\Connection
factory_service: doctrine_mongodb.odm.log_connection
factory_method: getMongoClient
/app/config_dev.yml
In this example I decided to store everything (
debug
level) as always into thedev.log
and just errors, warnings and notices on mongo.
monolog:
handlers:
main:
type: stream
path: "%kernel.logs_dir%/%kernel.environment%.log"
level: debug
console:
type: console
bubble: false
verbosity_levels:
VERBOSITY_VERBOSE: INFO
VERBOSITY_VERY_VERBOSE: DEBUG
channels: ["!doctrine"]
console_very_verbose:
type: console
bubble: false
verbosity_levels:
VERBOSITY_VERBOSE: NOTICE
VERBOSITY_VERY_VERBOSE: NOTICE
VERBOSITY_DEBUG: DEBUG
channels: ["doctrine"]
mongo:
type: mongo
level: notice # change as desired
mongo:
id: mongolog
database: %mongodb_database%
collection: logs
/app/config_prod.yml
monolog:
handlers:
main:
type: fingers_crossed
action_level: error
handler: mongo
nested:
type: stream
path: "%kernel.logs_dir%/%kernel.environment%.log"
level: debug
console:
type: console
mongo:
type: mongo
level: notice
mongo:
id: mongolog
database: %mongodb_database%
collection: logs
Now let's trigger a PHP notice and check if it'll be stored on MongoDB properly :-)
<?php trigger_error('hello world!', E_USER_NOTICE);
Adding HTTP request headers to Monolog record
/app/services.yml
kernel.listener.exception_listener:
class: AppBundle\EventListener\ExceptionListener
arguments:
- @logger
tags:
- { name: kernel.event_listener, event: kernel.exception, method: onKernelException }
AppBundle\EventListener\ExceptionListener
<?php
namespace AppBundle\EventListener;
use Monolog\Handler\MongoDBHandler;
use Symfony\Bridge\Monolog\Logger;
use Symfony\Component\Debug\ExceptionHandler;
use Symfony\Component\HttpKernel\Event\GetResponseForExceptionEvent;
/**
* Class ExceptionListener
* @package AppBundle\EventListener
* @author Francesco Casula <fra.casula@gmail.com>
*/
class ExceptionListener extends ExceptionHandler
{
/**
* @var Logger
*/
private $logger;
/**
* @param Logger $logger
*/
public function __construct(Logger $logger)
{
$this->logger = $logger;
}
/**
* @return Logger
*/
public function getLogger()
{
return $this->logger;
}
/**
* @param GetResponseForExceptionEvent $event
*/
public function onKernelException(GetResponseForExceptionEvent $event)
{
foreach ($this->getLogger()->getHandlers() as $handler) {
if ($handler instanceof MongoDBHandler) {
$handler->pushProcessor(function (array $record) use ($event) {
$record['extra']['headers'] = $event->getRequest()->headers->all();
return $record;
});
break;
}
}
}
}

Francesco Casula
- 26,184
- 15
- 132
- 131
-
Francesco, this is really cool and, as far as I can say, it works. One question though. How to ready this data? There is no Document Object in your tutorial/configuration, so is it possible to read from MongoDB using Doctrine without these objects? Just raw data? How? – pawel.kalisz Apr 16 '16 at 11:45
-
Hi @pawel.kalisz, we've been using this method for quite some time in production. We're storing basically the exception with the whole stack trace and we found MongoChef to be a very good interface to connect to our MongoDB instance and go through the logs. Sometimes we also run the queries via the Mongo shell (command line). In that case just make sure you narrow down not just the record set but also its projection (db.collection.find second parameter, see https://docs.mongodb.org/manual/reference/method/db.collection.find/) – Francesco Casula Apr 16 '16 at 15:42
-
If you want to use just PHP I guess you can still use Doctrine or just the plain PHP Mongo classes. – Francesco Casula Apr 16 '16 at 15:44