diff --git a/src/Monolog/Handler/PsrHandler.php b/src/Monolog/Handler/PsrHandler.php index a9780b01..e0c67dcd 100644 --- a/src/Monolog/Handler/PsrHandler.php +++ b/src/Monolog/Handler/PsrHandler.php @@ -13,13 +13,18 @@ namespace Monolog\Handler; use Monolog\Logger; use Psr\Log\LoggerInterface; +use Monolog\Formatter\FormatterInterface; /** * Proxies log messages to an existing PSR-3 compliant logger. * + * If a formatter is configured, the formatter's output MUST be a string and the + * formatted message will be fed to the wrapped PSR logger instead of the original + * log record's message. + * * @author Michael Moussa */ -class PsrHandler extends AbstractHandler +class PsrHandler extends AbstractHandler implements FormattableHandlerInterface { /** * PSR-3 compliant logger @@ -28,6 +33,11 @@ class PsrHandler extends AbstractHandler */ protected $logger; + /** + * @var FormatterInterface + */ + protected $formatter; + /** * @param LoggerInterface $logger The underlying PSR-3 compliant logger to which messages will be proxied * @param string|int $level The minimum logging level at which this handler will be triggered @@ -49,8 +59,39 @@ class PsrHandler extends AbstractHandler return false; } - $this->logger->log(strtolower($record['level_name']), $record['message'], $record['context']); + if ($this->formatter) { + $formatted = $this->formatter->format($record); + $this->logger->log(strtolower($record['level_name']), (string) $formatted, $record['context']); + } else { + $this->logger->log(strtolower($record['level_name']), $record['message'], $record['context']); + } return false === $this->bubble; } + + /** + * Sets the formatter. + * + * @param FormatterInterface $formatter + */ + public function setFormatter(FormatterInterface $formatter): HandlerInterface + { + $this->formatter = $formatter; + + return $this; + } + + /** + * Gets the formatter. + * + * @return FormatterInterface + */ + public function getFormatter(): FormatterInterface + { + if (!$this->formatter) { + throw new \LogicException('No formatter has been set and this handler does not have a default formatter'); + } + + return $this->formatter; + } } diff --git a/tests/Monolog/Handler/PsrHandlerTest.php b/tests/Monolog/Handler/PsrHandlerTest.php index e371512d..bebaa71d 100644 --- a/tests/Monolog/Handler/PsrHandlerTest.php +++ b/tests/Monolog/Handler/PsrHandlerTest.php @@ -13,6 +13,7 @@ namespace Monolog\Handler; use Monolog\Test\TestCase; use Monolog\Logger; +use Monolog\Formatter\LineFormatter; /** * @covers Monolog\Handler\PsrHandler::handle @@ -47,4 +48,21 @@ class PsrHandlerTest extends TestCase $handler = new PsrHandler($psrLogger); $handler->handle(['level' => $level, 'level_name' => $levelName, 'message' => $message, 'context' => $context]); } + + public function testFormatter() + { + $message = 'Hello, world!'; + $context = ['foo' => 'bar']; + $level = Logger::ERROR; + $levelName = 'error'; + + $psrLogger = $this->createMock('Psr\Log\NullLogger'); + $psrLogger->expects($this->once()) + ->method('log') + ->with(strtolower($levelName), 'dummy', $context); + + $handler = new PsrHandler($psrLogger); + $handler->setFormatter(new LineFormatter('dummy')); + $handler->handle(['level' => $level, 'level_name' => $levelName, 'message' => $message, 'context' => $context, 'extra' => [], 'date' => new \DateTimeImmutable()]); + } }