Sends your logs to files, sockets, inboxes, databases and various web services

Last update: May 19, 2022

Monolog - Logging for PHP Continuous Integration

Total Downloads Latest Stable Version

Monolog sends your logs to files, sockets, inboxes, databases and various web services. See the complete list of handlers below. Special handlers allow you to build advanced logging strategies.

This library implements the PSR-3 interface that you can type-hint against in your own libraries to keep a maximum of interoperability. You can also use it in your applications to make sure you can always use another compatible logger at a later time. As of 1.11.0 Monolog public APIs will also accept PSR-3 log levels. Internally Monolog still uses its own level scheme since it predates PSR-3.


Install the latest version with

$ composer require monolog/monolog

Basic Usage


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

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

// add records to the log


Support Monolog Financially

Get supported Monolog and help fund the project with the Tidelift Subscription or via GitHub sponsorship.

Tidelift delivers commercial support and maintenance for the open source dependencies you use to build your applications. Save time, reduce risk, and improve code health, while paying the maintainers of the exact dependencies you use.

Third Party Packages

Third party handlers, formatters and processors are listed in the wiki. You can also add your own there if you publish one.



  • Monolog ^2.0 works with PHP 7.2 or above, use Monolog ^1.25 for PHP 5.3+ support.


Monolog 1.x support is somewhat limited at this point and only important fixes will be done. You should migrate to Monolog 2 where possible to benefit from all the latest features and fixes.

Submitting bugs and feature requests

Bugs and feature request are tracked on GitHub

Framework Integrations


Jordi Boggiano - [email protected] -
See also the list of contributors who participated in this project.


Monolog is licensed under the MIT License - see the LICENSE file for details


This library is heavily inspired by Python's Logbook library, although most concepts have been adjusted to fit to the PHP world.

  • 1. Add new Slack handlers using Slackbot and webhooks


    This is keeping the previous SlackHandler, but extracts the message formatting logic and introduces two new Slack handlers:

    • SlackbotHandler - this is the simplest way to log to Slack and most people could use that. It doesn't allow fancy formatting, but has autolinking and the simplest configuration with two clicks in the Slack settings and getting a token.
    • SlackWebhookHandler - This is a bit more advanced as it allows for the same formatting and adding attachements as the SlackHandler, but it uses the Slack Webhooks which are quite easier to set up than the OAuth API. The minimum it requires is a webhook URL which is a retrievable with about two clicks in the Slack settings. Even the channel is optional as it could be configured in the integration.

    This is probably not the leanest way to implement what we've discussed in, but after working at this I believe this is the simplest and the right approach.

    While we could implement everything in one handler the API would become horrible and it would be harder to understand from users. Providing choice with simple to use separate classes is better IMHO. Apart from this the SlackHandler extends the SocketHandler and the webhooks and the Slackbot wouldn't work nicely with that.

    What do you think?

    @Seldaek @gkedzierski @Gummibeer @nisbeti

    • [x] Extracting Slack formatting logic in SlackRecord
    • [x] SlackbotHandler
    • [x] SlackWebhookHandler
    • [x] Refactor SlackHandler using the new SlackRecord
    • [x] Add new handlers to the docs
    • [x] Unit tests of SlackRecord
    • [x] Unit tests for SlackbotHandler
    • [x] Unit tests for SlackWebhookHandler
    • [x] Update unit tests for SlackHandler
    Reviewed by hkdobrev at 2016-09-06 21:00
  • 2. Added an handler for NewRelic

    • implemented a test which verifies that the fallback handler handles records when the NewRelic PHP extension is not installes
    • implemented the actual handler

    There are a few problems that Id like to discuss:

    • how to properly test it? The NewRelic extension is proprietary, so you cannot obtain it for free
    • do we need the fallback handler? It would be super useful for local development, since developers dont usually get the NR extension on their local machines - at the same time I recognize that there is no fallback handler for other handlers (ie Graylog2)
    • currently, that test seems a little bit too weak to be called a "test"
    • if we use function_exists we could add some more meaningful tests, but at the same time extension_loaded is more right
    Reviewed by odino at 2012-08-22 20:50
  • 3. Suppress warnings on date_default_timezone_get()

    Unfortunately date_default_timezone_get() still triggers the classic timezone warning, and there is no other way to determine if a timezone has been set.

    While one can ensure their projects always perform a date_default_timezone_set() there are still common places where monolog can be imported without direct user control over setting default timezones.

    In my particular case, including monolog in a Symfony2 composer project with the stock Symfony2 post-install-cmd and post-update-cmd chain causes failures at the end of an install/update cycle. I believe it's composer in this case that translates all triggered warnings/errors into exceptions which causes whatever process that is running to fail.

    Therefore I propose we just suppress the warnings from date_default_timezone_set() for now.

    In the future timezone management should maybe be mildly refactored to be injectable and default to UTC, but this will eliminate

    Reviewed by dcousineau at 2012-09-27 18:00
  • 4. Added a new ResettableInterface and implemented it where possible.

    Added a new ResetableInterface and implemented it where possible.

    When one use Monolog in a long process like an AMQP worker with a FingersCrossedHandler or BufferHandler there is a drawback: as soon as there is an AMQP message that generate a log >= error (for example), all next AMQP messages will output logs, even if theses messages don't generate log where level >= error.

    In the same context there is a drawback for processor that add an UUID to the logs. The UUID should change for each AMQP messages.

    This patch address this issue with a new interface: ResettableInterface interface. Side note: reset(), flush(), clear(), are already used in Monolog. So basically, one can use the reset() on the Logger and on some Handlers / Processors.

    It's especially useful for

    • the FingersCrossedHandler: it close() the buffer, then it clear() the buffer.
    • the BufferHandler: it flush() the buf
    Reviewed by lyrixx at 2017-05-31 15:51
  • 5. 2.0 Code cleanups / tasks

    • [x] ~~Clean up arg orders of handlers that have had added args pushed at the end (after bubbling etc), maybe group them in an $options array or parameter objects? Needs RFC. Check #801 too about fluent setters~~
    • [x] add scalar hints and return type hints where relevant ("only" handlers left to go through)
    • [x] ~~figure out how to handle network timeouts globally somehow, see #733~~
    • [x] Add a close() method on the Logger to close all its handlers? What about resetting FingersCrossedHandler?
    • [x] Define which php version should be supported (=> 7.1)
    • [x] Add a timezone arg to Logger instead of the static timezone?
    • [x] Turn static::getLevelName into static::
    • [x] Set Monolog\Logger::API = 2 to allow users to adjust
    • [x] Remove non PSR-3 methods to add record
    • [x] Remove processor/formatter setters and getters from the HandlerInterface
    • [x] Remove logstash V0 support or at least make V1 default
    • [x] Remove legacy GELF handler support, c.f. #326
    • [x] Remove datetime TODO in loggly handler
    • [x] Move Monolog\TestCase to src/, see
    • [x] ~~Split handlers w/ dependencies into packages i.e.
    • [x] ~~Change Logger constants to have RFC values (
    • [x] Remove substr TODO in AmqpHandler
    • [x] Remove default handler ($this->pushHandler(new StreamHandler('php://stderr', static::DEBUG));) from Monolog\Logger
    • [x] ~~Consider adding a public method (send or write or so) on handlers to make reusing them out of monolog easier, c.f.~~
    • [x] Consider using MongoDBFormatter as default in MongoDBHandler
    • [x] Drop support for outdated mongo exts in MongoDBHandler
    • [x] Remove BC __get() in SwiftMailerHandler
    • [x] Update HipChat to API v2 using 01549ec4d05e2d3f33227531d9fc9454d5ef6049 and room_id and from in buildContent (+ nickname everywhere) should be removed. See if we can't detect the token format and warn users using a v1 token.
    • [x] Check all PHP_VERSION and version_compare checks for relevance
    • [x] LineFormatter when showing stack traces should show new lines on new lines, and not the exception as part of the context that gets inlined into json => #752
    • [x] Consider removing useless PHP docs if the scalar + return type hints give enough info
    • [x] Disable microseconds timestamps by default?

    php7 ideas:

    • [x] treat Error-class exceptions in a special way as they are replacing E_COMPILE_ERROR and such from defaultErrorLevelMap
    • [x] ~~possibly remove ErrorHandler::registerFatalHandler if this is not needed anymore~~
    • [x] enable strict mode everywhere?

    ~~those items have been abandoned~~

    Reviewed by Seldaek at 2013-05-21 18:25
  • 6. Getting token to use Monolog with Slack

    It is not straight forward to get a token to use monolog with Slack. The expectation is that you write an OAuth client to get the token, but it is possible to get it manually. These are the steps I followed today:

    You should already have an account and a channel set up that you want to send error messages to.

    1. Create a new Slack App - which will give you a client_id and a client_secret which you need for step two. You will need to enter a redirect URI, which can be any page for this purpose.
    2. Got to[client_id]&scope=chat:write:bot
    3. Authorise App on the page that is returned.
    4. From the URI copy the code that is returned.
    5. Go to[client_id]&client_secret=[client_secret]&code=[code]
    6. Your token is in the JSON that is displayed.

    TO debug errors insert echo fread($this->resource, 1000); at the end of the writeToSocket method of Monolog/Handler/SocketHandler (see

    Reviewed by nisbeti at 2016-03-14 15:38
  • 7. FirePHP 1.0 support

    I added support for FirePHP 1.0 to the FirePHP handler along with instructions in the README.

    The handler will now use FirePHP 1.0 if detected instead of the built-in protocol implementation. There are many advantages to this including:

    • Encoding of complex variables
    • File and line info
    • Support for large numbers of log messages
    • Support for evolving Companion client tools

    Coming soon:

    • Conditional logging where the client can enable and disable log handlers on request

    Try it out, let me know what you think. I would be happy to maintain this integration and add to it over time.

    I hope you are enjoying your time away!


    Reviewed by cadorn at 2011-05-12 16:35
  • 8. Logstash throws error with json codec due time format

    Here's an error that logstash 1.3.2 throws using V1 LogstashFormatter:

    A plugin had an unrecoverable error. Will restart this plugin.
      Plugin: <LogStash::Inputs::File path=>["/Users/simas/Sites/kibana/logger/logs/app.log"], type=>"app", start_position=>"end">
      Error: Invalid format: "2013-12-29T22:11:23.429748+02:00" is malformed at "748+02:00" {:level=>:error}

    Seems that logstash expects UTC timestamp without timezone, somethning like this: 2013-12-29T22:11:23.429Z

    Reviewed by saimaz at 2013-12-29 20:17
  • 9. Add support for handling PHP Errors, etc

    Examples of this are in Zend\Log and Raven_Client (Handles uncaught exceptions, fatal errors and PHP errors)

    Reviewed by davidwindell at 2013-05-24 17:35
  • 10. Sync RollbarHandler with the latest changes rollbar/rollbar package

    We received a request to update Monolog's RollbarHandler to be in sync with the latest version of our SDK ( ). The github issue can be found here:

    This PR makes the RollbarHandler up to date with rollbar-php v1.0+.

    Please, review and merge to master if it looks good to go.

    Reviewed by ArturMoczulski at 2017-08-16 05:15
  • 11. Added SimpleDBHandler

    I've added a SimpleDBHandler to log messages using a passed-in AmazonSDB object from the official Amazon SDK for PHP.

    Given the size limitations (which are gracious, but still exist) of SimpleDB domains, I've taken the approach of mapping log channels-to-SimpleDB domains.

    While SimpleDB has support for batch put operations, and the AmazonSDB class has support for sending items in parallel -- which, when combined, could conceivably allow for parallel batch puts -- I have kept this first commit simple, so that this handler's behavior mirrors that of most of the others.

    If it winds up being popular and users request it, I'd be happy to contribute a further SimpleDBBatchHandler that dives into supporting those scenarios.

    Meanwhile, I look forward to your feedback on this less complicated submission.

    Reviewed by claylo at 2012-09-09 03:38
  • 12. Fallback mechanic when handler fails

    Imagine a situation when you have 3 different handlers and you expect that the first handler is the main handler (logstash, for example). It's OK if Monolog successfully sends logs to the logstash, so, you don't need to block delivery to other handlers.

    But what if logstash handler fails? Connection timeouts, write timeouts, and so on... Usually, the system must make log records about this situation and must log the original log entry using fallback handlers (stderr or file, fo example).

    To do this we may add some an option like bubbleOnHandlingError that

    • blocks bubbling of a log entry if all is OK;
    • allows bubbling to the next handler if current handler fails and bubbleOnHandlingError is set.
    Reviewed by WoZ at 2022-05-21 09:23
  • 13. Bubbling is ignored when one of handlers in the chain fails

    Monolog version 1, 2, 3

    The default behavior is to ignore bubbling if something goes wrong inside a handler.

    Look at this part of the code.

    Imo, errors in some handlers must not affect other handlers if bubble options is set.

    Reviewed by WoZ at 2022-05-21 09:18
  • 14. RotatingFileHandler to maintain the correct maximum number files when using folder by date

    Setting filename format with slashes

    $handler = new RotatingFileHandler('path/to/save/sample.log', 2);
    $handler->setFilenameFormat('{date}/{filename}', 'Y/m/d');


    Reviewed by kermage at 2022-05-13 13:01
  • 15. Monolog doesn't handle E_USER_ERROR as fatal error if registerErrorHandler is called with callPrevious === false

    Monolog version 2.6


    $logger = new Monolog\Logger('main');
    $logger->pushHandler(new Monolog\Handler\StreamHandler('php://stderr', Monolog\Logger::DEBUG));
    $errorHandler = new ErrorHandler($logger);
    $errorHandler->registerErrorHandler([], false); // false is for callPrevious
    trigger_error('Error', E_USER_ERROR);


    1. $errorHandler->registerErrorHandler sets $this->previousErrorHandler to null.
    2. ErrorHandler::handleError() doesn't log error, but sets trace into the $this->lastFatalTrace. handleError assumes that the handleFatalError() will be called.
    3. callPrevious option prevents ErrorHandler::handleError() to start chaining, default PHP's error logger will not be called, handleError returns true. This prevents PHP from setting "last error" structure internally.
    4. ErrorHandler::handleFatalError() catches E_USER_ERROR and tries to receive $lastError = error_get_last();, but there's no last error.
    5. Both functions ignores error logging.

    Scenario. I use official docker php image with error_log == 'php://stderr'. Also, I want to use Monolog with StreamHandler and write logs to stderr. Monolog logs errors twice with default settings (first time default PHP logger writes logs to stderr, second time Monolog does the same).

    Reviewed by WoZ at 2022-05-11 15:41
  • 16. Unable to send email with NativeMailerHandler in Laravel 8

    Monolog version 2 Laravel 8.x Php 7.4

    Hi, I'm trying to use a laravel logging channel to send an email with the error, but I can't get anything to be sent, I'm trying with monolog and NativeMailerHandler but I still can't send anything, Laravel 8 and php 7.4:


    'monolog' => [
                'driver' => 'monolog',
                'handler' =>\Monolog\Handler\NativeMailerHandler::class,
                'level' => 'debug',
                'with' => [
                    'to' => '[email protected]',
                    'from' => '[email protected]',
                    'subject' => 'test',
                    'level' => 'debug'

    Call from a controller


    In the .env i have the mails settings:

    [email protected]
    [email protected]

    It simply does not send any message, nor does it give any error or anything...

    Reviewed by julianphp at 2022-04-27 06:07
Related tags
Keep your laravel logs small and tidy.

Logs can get quite out of hand. This package helps save server space and keep your Laravel log files small.

Apr 8, 2022
Clear all your logs in [linux/windows] servers 🛡️
Clear all your logs in [linux/windows] servers 🛡️

Log-killer Log Killer is tool for [Linux/Windows] Servers This tool will delete all your logs just download the tool and run it on the server if your

May 7, 2022
Capture and monitor detailed error logs with nice dashboard and UI
 Capture and monitor detailed error logs with nice dashboard and UI

Capture and monitor detailed error logs with nice dashboard and UI Requirements Check Laravel 6 requirements Check Laravel 7 requirements Installation

Apr 7, 2022
Paste, share and analyse Minecraft server logs Paste, share & analyse your Minecraft server logs About The project was created in 2017 by the Aternos team after more than 4 years of

May 15, 2022
Logs which process created or modified a record

It is sometimes very useful to know which process created or modified a particular record in your database. This package provides a trait to add to your Laravel models which automatically logs that for you.

Feb 12, 2022
Small package that can helps in debugging with API logs for Laravel Project.

Rest APIs Logger This is a small package that can helps in debugging with API logs. Installation Install the package via composer composer require tfs

Oct 28, 2021
Small laravel package for viewing api logs which can be used in debugging.
Small laravel package for viewing api logs which can be used in debugging.

This is a small package that can helps in debugging api logs. It can log request method, url, duration, request payload, which models are retrieved, controller and method.

Mar 31, 2022
Small tool that extracts witness data from Helium miner logs.

Helium Miner Logs Analyzer Small tool that extracts witness data from Helium miner logs. It currently works for the Pisces 100 and miner version miner

May 20, 2022
Allows you to process logs using any PSR-3 compatible logger such as Monolog

Yii 2 PSR Log Target Allows you to process logs using any PSR-3 compatible logger such as Monolog

Apr 8, 2022
123Solar is a set of PHP/JS files that make a web logger to monitor your photovoltaic inverter(s)

123Solar is a set of PHP/JS files that make a web logger to monitor your photovoltaic inverter(s). It just need a web server and PHP, no databases are even needed. The philosophy is: To keep it simple, fast, with a low foot print to run on cheap and low powered devices.

May 5, 2022
DatabaseLog CakePHP plugin to log into DB instead of files. Better to filter and search.

CakePHP DatabaseLog Plugin DatabaseLog engine for CakePHP applications. This branch is for CakePHP 4.0+. See version map for details. Features Easy se

Dec 4, 2021
Laravel logger is an activity event logger for your Laravel or Lumen application
Laravel logger is an activity event logger for your Laravel or Lumen application

Laravel logger is an activity event logger for your Laravel or Lumen application. It comes out the box with ready to use with dashboard to view your activity. Laravel logger can be added as a middleware or called through a trait. Easily have an Activity Log. This package is easily configurable and customizable. Supports Laravel 5.3, 5.4, 5.5, 5.6, 5.7, 5.8, 6, and 7+

May 24, 2022
PHP logging library that is highly extendable and simple to use.

Analog - Minimal PHP logging library Copyright: (c) 2012-Present Johnny Broadway License: MIT A minimal PHP logging package based on the idea of using

Apr 10, 2022
Flexible and rock solid audit log tracking for CakePHP 3

AuditStash Plugin For CakePHP This plugin implements an "audit trail" for any of your Table classes in your application, that is, the ability of recor

Nov 27, 2021
Log Laravel application request and response with a unique ID for easy debugging
Log Laravel application request and response with a unique ID for easy debugging

Flexible and extendable logging of Laravel application request and responses Zero configuration logging of Requests and Responses to database or custo

Jan 25, 2022
A simple and beautiful laravel log reader
A simple and beautiful laravel log reader

Laravel Log Reader A simple and beautiful laravel log reader Documentation Get full documentation of Laravel Log Reader Other Packages Laravel H - A h

May 9, 2022
Simple and lightweight OOP wrapper for PHP's low-level sockets extension (ext-sockets)

clue/socket-raw Simple and lightweight OOP wrapper for PHP's low-level sockets extension (ext-sockets). PHP offers two networking APIs, the newer stre

May 5, 2022
DataLoaderPhp is a generic utility to be used as part of your application's data fetching layer to provide a simplified and consistent API over various remote data sources such as databases or web services via batching and caching.

DataLoaderPHP is a generic utility to be used as part of your application's data fetching layer to provide a simplified and consistent API over various remote data sources such as databases or web services via batching and caching.

May 18, 2022
Amazon Web Services CloudWatch Logs Handler for Monolog library

AWS CloudWatch Logs Handler for Monolog Handler for PHP logging library Monolog for sending log entries to AWS CloudWatch Logs service. Before using t

May 16, 2022