diff options
24 files changed, 672 insertions, 395 deletions
diff --git a/README.mdown b/README.mdown index 73d5861..b3339f8 100644 --- a/README.mdown +++ b/README.mdown @@ -5,28 +5,20 @@ Usage ----- use Monolog\Logger; - use Monolog\Log; - use Monolog\Writer\FileWriter; - use Monolog\Formatter\SimpleFormatter; + use Monolog\Handler\FileHandler; - // create a log with writers/formatters - $writer = new FileWriter('path/to/your.log'); - $writer->setFormatter(new SimpleFormatter()); - $log = new Log('name', Logger::WARN, $writer); + // create a log channel + $log = new Logger('name'); + $log->pushHandler(new FileHandler('path/to/your.log', Logger::WARNING)); - // create a logger with one or more logs - $logger = new Logger(array($log)); - - // write to all logs - $logger->addWarning('Foo'); - - // write only to the 'name' log - $logger->addError('Bar', 'name'); + // add messages to the log + $log->addWarning('Foo'); + $log->addError('Bar'); Todo ---- -- Log rotation for FileWriter +- Log rotation for RotatingFileHandler - FirePHP writer - Syslog writer @@ -43,4 +35,9 @@ Monolog is licensed under the MIT License - see the LICENSE file for details Requirements ------------ -Any flavor of PHP5.3 should do +Any flavor of PHP 5.3 should do + +Acknowledgements +---------------- + +This library is heavily inspired by Python's Logbook library, although it has been adapted to fit in PHP. diff --git a/src/Monolog/Formatter/FormatterInterface.php b/src/Monolog/Formatter/FormatterInterface.php index 1fa15e2..fd8233f 100644 --- a/src/Monolog/Formatter/FormatterInterface.php +++ b/src/Monolog/Formatter/FormatterInterface.php @@ -13,5 +13,5 @@ namespace Monolog\Formatter; interface FormatterInterface { - function format($log, $message); + function format($message); } diff --git a/src/Monolog/Formatter/JsonFormatter.php b/src/Monolog/Formatter/JsonFormatter.php new file mode 100644 index 0000000..335145c --- /dev/null +++ b/src/Monolog/Formatter/JsonFormatter.php @@ -0,0 +1,23 @@ +<?php
+
+/*
+ * This file is part of the Monolog package.
+ *
+ * (c) Jordi Boggiano <j.boggiano@seld.be>
+ *
+ * For the full copyright and license information, please view the LICENSE
+ * file that was distributed with this source code.
+ */
+
+namespace Monolog\Formatter;
+
+use Monolog\Logger;
+
+class JsonFormatter implements FormatterInterface
+{
+ public function format($message)
+ {
+ $message['message'] = json_encode($message['message']);
+ return $message;
+ }
+}
diff --git a/src/Monolog/Formatter/SimpleFormatter.php b/src/Monolog/Formatter/LineFormatter.php index 3a2d2ee..e272fdc 100644 --- a/src/Monolog/Formatter/SimpleFormatter.php +++ b/src/Monolog/Formatter/LineFormatter.php @@ -13,9 +13,9 @@ namespace Monolog\Formatter; use Monolog\Logger; -class SimpleFormatter implements FormatterInterface +class LineFormatter implements FormatterInterface { - const SIMPLE_FORMAT = "[%date%] %log%.%level%: %message%\n"; + const SIMPLE_FORMAT = "[%datetime%] %channel%.%level_name%: %message%\n"; const SIMPLE_DATE = "Y-m-d H:i:s"; protected $format; @@ -27,25 +27,26 @@ class SimpleFormatter implements FormatterInterface $this->dateFormat = $dateFormat ?: self::SIMPLE_DATE; } - public function format($log, $message) + public function format($message) { - $defaults = array( - 'log' => $log, - 'level' => Logger::getLevelName($message['level']), - 'date' => date($this->dateFormat), - ); + $vars = $message; + $vars['datetime'] = $vars['datetime']->format($this->dateFormat); if (is_array($message['message'])) { - $vars = array_merge($defaults, $message['message']); - } else { - $vars = $defaults; - $vars['message'] = $message['message']; + unset($vars['message']); + $vars = array_merge($vars, $message['message']); } - $message = $this->format; + $output = $this->format; foreach ($vars as $var => $val) { - $message = str_replace('%'.$var.'%', $val, $message); + if (!is_array($val)) { + $output = str_replace('%'.$var.'%', $val, $output); + } } + foreach ($vars['extra'] as $var => $val) { + $output = str_replace('%extra.'.$var.'%', $val, $output); + } + $message['message'] = $output; return $message; } } diff --git a/src/Monolog/Handler/AbstractHandler.php b/src/Monolog/Handler/AbstractHandler.php new file mode 100644 index 0000000..90ff415 --- /dev/null +++ b/src/Monolog/Handler/AbstractHandler.php @@ -0,0 +1,121 @@ +<?php + +/* + * This file is part of the Monolog package. + * + * (c) Jordi Boggiano <j.boggiano@seld.be> + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Monolog\Handler; + +use Monolog\Logger; +use Monolog\Formatter\LineFormatter; + +abstract class AbstractHandler implements HandlerInterface +{ + protected $level; + protected $bubble; + protected $parent; + + protected $formatter; + protected $processor; + + public function __construct($level = Logger::DEBUG, $bubble = false) + { + $this->level = $level; + $this->bubble = $bubble; + } + + public function handle($message) + { + if ($message['level'] < $this->level) { + return false; + } + + if ($this->processor) { + $message = call_user_func($this->processor, $message, $this); + } + + if (!$this->formatter) { + $this->formatter = $this->getDefaultFormatter(); + } + $message = $this->formatter->format($message); + + $this->write($message); + return false === $this->bubble; + } + + abstract public function write($message); + + public function close() + { + } + + public function setProcessor($callback) + { + $this->processor = $callback; + } + + public function getProcessor() + { + return $this->processor; + } + + public function setFormatter($formatter) + { + $this->formatter = $formatter; + } + + public function getFormatter() + { + return $this->formatter; + } + + public function setLevel($level) + { + $this->level = $level; + } + + public function getLevel() + { + return $this->level; + } + + public function setBubble($bubble) + { + $this->bubble = $bubble; + } + + public function getBubble() + { + return $this->bubble; + } + + public function getParent() + { + return $this->parent; + } + + /** + * Sets the parent handler + * + * @param Monolog\Handler\HandlerInterface + */ + public function setParent(HandlerInterface $parent) + { + $this->parent = $parent; + } + + public function __destruct() + { + $this->close(); + } + + protected function getDefaultFormatter() + { + return new LineFormatter(); + } +} diff --git a/src/Monolog/Handler/HandlerInterface.php b/src/Monolog/Handler/HandlerInterface.php new file mode 100644 index 0000000..81cff1f --- /dev/null +++ b/src/Monolog/Handler/HandlerInterface.php @@ -0,0 +1,29 @@ +<?php + +/* + * This file is part of the Monolog package. + * + * (c) Jordi Boggiano <j.boggiano@seld.be> + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Monolog\Handler; + +interface HandlerInterface +{ + public function handle($message); + + public function setLevel($level); + + public function getLevel(); + + public function setBubble($bubble); + + public function getBubble(); + + public function getParent(); + + public function setParent(HandlerInterface $parent); +} diff --git a/src/Monolog/Handler/NullHandler.php b/src/Monolog/Handler/NullHandler.php new file mode 100644 index 0000000..cd7229e --- /dev/null +++ b/src/Monolog/Handler/NullHandler.php @@ -0,0 +1,29 @@ +<?php + +/* + * This file is part of the Monolog package. + * + * (c) Jordi Boggiano <j.boggiano@seld.be> + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Monolog\Handler; + +use Monolog\Logger; + +class NullHandler extends AbstractHandler +{ + public function handle($message) + { + if ($message['level'] < $this->level) { + return false; + } + return false === $this->bubble; + } + + public function write($message) + { + } +}
\ No newline at end of file diff --git a/src/Monolog/Writer/FileWriter.php b/src/Monolog/Handler/RotatingFileHandler.php index 14993f0..694744d 100644 --- a/src/Monolog/Writer/FileWriter.php +++ b/src/Monolog/Handler/RotatingFileHandler.php @@ -9,20 +9,13 @@ * file that was distributed with this source code. */ -namespace Monolog\Writer; +namespace Monolog\Handler; -class FileWriter extends StreamWriter +class RotatingFileHandler extends StreamHandler { protected $rotation; protected $maxAge; - public function __construct($file, $rotation = null, $maxAge = null) - { - parent::__construct($file); - $this->rotation = $rotation; - $this->maxAge = $maxAge; - } - public function close() { parent::close(); diff --git a/src/Monolog/Handler/StreamHandler.php b/src/Monolog/Handler/StreamHandler.php new file mode 100644 index 0000000..1a1d527 --- /dev/null +++ b/src/Monolog/Handler/StreamHandler.php @@ -0,0 +1,53 @@ +<?php + +/* + * This file is part of the Monolog package. + * + * (c) Jordi Boggiano <j.boggiano@seld.be> + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Monolog\Handler; + +use Monolog\Formatter\SimpleFormatter; +use Monolog\Logger; + +class StreamHandler extends AbstractHandler +{ + protected $stream; + protected $url; + + public function __construct($stream, $level = Logger::DEBUG, $bubble = true) + { + parent::__construct($level, $bubble); + if (is_resource($stream)) { + $this->stream = $stream; + } else { + $this->url = $stream; + } + } + + public function write($message) + { + if (null === $this->stream) { + if (!$this->url) { + throw new \LogicException('Missing stream url, the stream can not be opened. This may be caused by a premature call to close().'); + } + $this->stream = fopen($this->url, 'a'); + if (!is_resource($this->stream)) { + throw new \UnexpectedValueException('The stream could not be opened, "'.$this->url.'" may be an invalid url.'); + } + } + fwrite($this->stream, (string) $message['message']); + } + + public function close() + { + if (null !== $this->stream) { + fclose($this->stream); + $this->stream = null; + } + } +}
\ No newline at end of file diff --git a/src/Monolog/Log.php b/src/Monolog/Log.php deleted file mode 100644 index 253cf7d..0000000 --- a/src/Monolog/Log.php +++ /dev/null @@ -1,59 +0,0 @@ -<?php - -/* - * This file is part of the Monolog package. - * - * (c) Jordi Boggiano <j.boggiano@seld.be> - * - * For the full copyright and license information, please view the LICENSE - * file that was distributed with this source code. - */ - -namespace Monolog; - -use Monolog\Writer\WriterInterface; - -class Log -{ - protected $level; - protected $name; - protected $writers; - - public function __construct($name, $level = Logger::WARNING, $writers = array()) - { - $this->name = $name; - // TODO move level down to the writers - $this->level = $level; - $this->writers = is_array($writers) ? $writers : array($writers); - } - - public function getName() - { - return $this->name; - } - - public function addWriter(WriterInterface $writer) - { - $this->writers[] = $writer; - } - - public function addMessage($level, $message) - { - if ($level < $this->level) { - return; - } - foreach ($this->writers as $writer) { - $writer->write($this->name, $level, $message); - } - } - - public function setLevel($level) - { - $this->level = $level; - } - - public function getLevel() - { - return $this->level; - } -} diff --git a/src/Monolog/Logger.php b/src/Monolog/Logger.php index a220c87..93349e2 100644 --- a/src/Monolog/Logger.php +++ b/src/Monolog/Logger.php @@ -11,6 +11,9 @@ namespace Monolog; +use Monolog\Handler\HandlerInterface; +use Monolog\Handler\StreamHandler; + class Logger { /** @@ -42,104 +45,124 @@ class Logger 400 => 'ERROR', ); - protected $logs; + protected $name; + + /** + * The handler instance at the top of the handler stack + * + * @var Monolog\Handler\HandlerInterface + */ + protected $handler; - public function __construct($logs = array()) + public function __construct($name) { - $this->logs = array(); - if (!is_array($logs)) { - $logs = array($logs); - } - foreach ($logs as $log) { - $this->logs[$log->getName()] = $log; + $this->name = $name; + } + + public function pushHandler(HandlerInterface $handler) + { + if ($this->handler) { + $handler->setParent($this->handler); } + $this->handler = $handler; } - public function addLog(Log $log) + public function popHandler() { - $this->logs[$log->getName()] = $log; + if (null === $this->handler) { + throw new \LogicException('You tried to pop from an empty handler stack.'); + } + $top = $this->handler; + $this->handler = $top->getParent(); + return $top; } - public function addMessage($level, $message, $log = null) + public function addMessage($level, $message) { + if (null === $this->handler) { + $this->pushHandler(new StreamHandler('php://stderr', self::DEBUG)); + } $message = array( 'message' => $message, 'level' => $level, + 'level_name' => $this->getLevelName($level), + 'channel' => $this->name, + 'datetime' => new \DateTime(), + 'extra' => array(), ); - if (null === $log) { - $logs = $this->logs; - } else { - $logs = is_array($log) ? array_flip($log) : array($log => true); - } - foreach ($logs as $log => $dummy) { - $this->logs[$log]->log($level, $message); + $handled = false; + $handler = $this->handler; + while ($handler && true !== $handled) { + $handled = (bool) $handler->handle($message); + $handler = $handler->getParent(); } + return $handled; } - public function addDebug($message, $log = null) + public function addDebug($message, $channel = 'default') { - $this->addMessage(self::DEBUG, $message, $log); + $this->addMessage(self::DEBUG, $message, $channel); } - public function addInfo($message, $log = null) + public function addInfo($message, $channel = 'default') { - $this->addMessage(self::INFO, $message, $log); + $this->addMessage(self::INFO, $message, $channel); } - public function addWarning($message, $log = null) + public function addWarning($message, $channel = 'default') { - $this->addMessage(self::WARNING, $message, $log); + $this->addMessage(self::WARNING, $message, $channel); } - public function addError($message, $log = null) + public function addError($message, $channel = 'default') { - $this->addMessage(self::ERROR, $message, $log); + $this->addMessage(self::ERROR, $message, $channel); } - public static function getLevelName($level) + public function getLevelName($level) { return self::$levels[$level]; } // ZF Logger Compat - public function debug($message, $log = null) + public function debug($message, $channel = null) { - $this->addMessage(self::DEBUG, $message, $log); + $this->addMessage(self::DEBUG, $message, $channel); } - public function info($message, $log = null) + public function info($message, $channel = 'default') { - $this->addMessage(self::INFO, $message, $log); + $this->addMessage(self::INFO, $message, $channel); } - public function notice($message, $log = null) + public function notice($message, $channel = 'default') { - $this->addMessage(self::INFO, $message, $log); + $this->addMessage(self::INFO, $message, $channel); } - public function warn($message, $log = null) + public function warn($message, $channel = 'default') { - $this->addMessage(self::WARNING, $message, $log); + $this->addMessage(self::WARNING, $message, $channel); } - public function err($message, $log = null) + public function err($message, $channel = 'default') { - $this->addMessage(self::ERROR, $message, $log); + $this->addMessage(self::ERROR, $message, $channel); } - public function crit($message, $log = null) + public function crit($message, $channel = 'default') { - $this->addMessage(self::ERROR, $message, $log); + $this->addMessage(self::ERROR, $message, $channel); } - public function alert($message, $log = null) + public function alert($message, $channel = 'default') { - $this->addMessage(self::ERROR, $message, $log); + $this->addMessage(self::ERROR, $message, $channel); } - public function emerg($message, $log = null) + public function emerg($message, $channel = 'default') { - $this->addMessage(self::ERROR, $message, $log); + $this->addMessage(self::ERROR, $message, $channel); } }
\ No newline at end of file diff --git a/src/Monolog/Processor/WebProcessor.php b/src/Monolog/Processor/WebProcessor.php new file mode 100644 index 0000000..d463494 --- /dev/null +++ b/src/Monolog/Processor/WebProcessor.php @@ -0,0 +1,28 @@ +<?php + +/* + * This file is part of the Monolog package. + * + * (c) Jordi Boggiano <j.boggiano@seld.be> + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Monolog\Processor; + +class WebProcessor +{ + public function __invoke($message, $handler) + { + $message['extra'] = array_merge( + $message['extra'], + array( + 'url' => $_SERVER['REQUEST_URI'], + 'ip' => $_SERVER['REMOTE_ADDR'], + 'method' => $_SERVER['REQUEST_METHOD'], + ) + ); + return $message; + } +} diff --git a/src/Monolog/Writer/NullWriter.php b/src/Monolog/Writer/NullWriter.php deleted file mode 100644 index c44a61f..0000000 --- a/src/Monolog/Writer/NullWriter.php +++ /dev/null @@ -1,29 +0,0 @@ -<?php - -/* - * This file is part of the Monolog package. - * - * (c) Jordi Boggiano <j.boggiano@seld.be> - * - * For the full copyright and license information, please view the LICENSE - * file that was distributed with this source code. - */ - -namespace Monolog\Writer; - -use Monolog\Formatter\FormatterInterface; - -class NullWriter implements WriterInterface -{ - public function write($log, $message) - { - } - - public function close() - { - } - - public function setFormatter(FormatterInterface $formatter) - { - } -}
\ No newline at end of file diff --git a/src/Monolog/Writer/StreamWriter.php b/src/Monolog/Writer/StreamWriter.php deleted file mode 100644 index 09d5203..0000000 --- a/src/Monolog/Writer/StreamWriter.php +++ /dev/null @@ -1,59 +0,0 @@ -<?php - -/* - * This file is part of the Monolog package. - * - * (c) Jordi Boggiano <j.boggiano@seld.be> - * - * For the full copyright and license information, please view the LICENSE - * file that was distributed with this source code. - */ - -namespace Monolog\Writer; - -use Monolog\Formatter\FormatterInterface; - -class StreamWriter implements WriterInterface -{ - protected $formatter; - protected $stream; - protected $url; - - public function __construct($streamUrl) - { - if (is_resource($streamUrl)) { - $this->stream = $streamUrl; - } else { - $this->url = $streamUrl; - } - } - - public function write($log, $message) - { - if (null === $this->stream) { - $this->stream = fopen($this->url, 'a'); - } - if ($this->formatter) { - $message = $this->formatter->format($log, $message); - } - fwrite($this->stream, (string) $message['message']); - } - - public function close() - { - fclose($this->stream); - $this->stream = null; - } - - public function setFormatter(FormatterInterface $formatter) - { - $this->formatter = $formatter; - } - - public function __destruct() - { - if (null !== $this->stream) { - $this->close(); - } - } -}
\ No newline at end of file diff --git a/src/Monolog/Writer/WriterInterface.php b/src/Monolog/Writer/WriterInterface.php deleted file mode 100644 index f8dffb3..0000000 --- a/src/Monolog/Writer/WriterInterface.php +++ /dev/null @@ -1,21 +0,0 @@ -<?php - -/* - * This file is part of the Monolog package. - * - * (c) Jordi Boggiano <j.boggiano@seld.be> - * - * For the full copyright and license information, please view the LICENSE - * file that was distributed with this source code. - */ - -namespace Monolog\Writer; - -use Monolog\Formatter\FormatterInterface; - -interface WriterInterface -{ - function setFormatter(FormatterInterface $formatter); - function write($log, $message); - function close(); -} diff --git a/tests/Monolog/Formatter/JsonFormatterTest.php b/tests/Monolog/Formatter/JsonFormatterTest.php new file mode 100644 index 0000000..df08ebe --- /dev/null +++ b/tests/Monolog/Formatter/JsonFormatterTest.php @@ -0,0 +1,30 @@ +<?php + +/* + * This file is part of the Monolog package. + * + * (c) Jordi Boggiano <j.boggiano@seld.be> + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Monolog\Formatter; + +use Monolog\Logger; + +class JsonFormatterTest extends \PHPUnit_Framework_TestCase +{ + public function testFormat() + { + $formatter = new JsonFormatter(); + $message = $formatter->format(array( + 'level_name' => 'WARNING', + 'channel' => 'log', + 'message' => array('foo'), + 'datetime' => new \DateTime, + 'extra' => array(), + )); + $this->assertEquals(json_encode(array('foo')), $message['message']); + } +} diff --git a/tests/Monolog/Formatter/LineFormatterTest.php b/tests/Monolog/Formatter/LineFormatterTest.php new file mode 100644 index 0000000..bc86302 --- /dev/null +++ b/tests/Monolog/Formatter/LineFormatterTest.php @@ -0,0 +1,47 @@ +<?php + +/* + * This file is part of the Monolog package. + * + * (c) Jordi Boggiano <j.boggiano@seld.be> + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Monolog\Formatter; + +use Monolog\Logger; + +class LineFormatterTest extends \PHPUnit_Framework_TestCase +{ + public function testDefFormatWithString() + { + $formatter = new LineFormatter(null, 'Y-m-d'); + $message = $formatter->format(array( + 'level_name' => 'WARNING', + 'channel' => 'log', + 'message' => 'foo', + 'datetime' => new \DateTime, + 'extra' => array(), + )); + $this->assertEquals('['.date('Y-m-d').'] log.WARNING: foo'."\n", $message['message']); + } + + public function testDefFormatWithArray() + { + $formatter = new LineFormatter(null, 'Y-m-d'); + $message = $formatter->format(array( + 'level_name' => 'ERROR', + 'channel' => 'meh', + 'datetime' => new \DateTime, + 'extra' => array(), + 'message' => array( + 'channel' => 'log', + 'level_name' => 'WARNING', + 'message' => 'foo', + ) + )); + $this->assertEquals('['.date('Y-m-d').'] log.WARNING: foo'."\n", $message['message']); + } +} diff --git a/tests/Monolog/Formatter/SimpleFormatterTest.php b/tests/Monolog/Formatter/SimpleFormatterTest.php deleted file mode 100644 index 5c7f76b..0000000 --- a/tests/Monolog/Formatter/SimpleFormatterTest.php +++ /dev/null @@ -1,38 +0,0 @@ -<?php - -/* - * This file is part of the Monolog package. - * - * (c) Jordi Boggiano <j.boggiano@seld.be> - * - * For the full copyright and license information, please view the LICENSE - * file that was distributed with this source code. - */ - -namespace Monolog\Formatter; - -use Monolog\Logger; - -class SimpleFormatterTest extends \PHPUnit_Framework_TestCase -{ - public function testDefFormatWithString() - { - $formatter = new SimpleFormatter(null, 'Y-m-d'); - $message = $formatter->format('log', array('level' => Logger::WARNING, 'message' => 'foo')); - $this->assertEquals('['.date('Y-m-d').'] log.WARNING: foo'."\n", $message); - } - - public function testDefFormatWithArray() - { - $formatter = new SimpleFormatter(null, 'Y-m-d'); - $message = $formatter->format('xx', array( - 'level' => Logger::ERROR, - 'message' => array( - 'log' => 'log', - 'level' => 'WARNING', - 'message' => 'foo', - ) - )); - $this->assertEquals('['.date('Y-m-d').'] log.WARNING: foo'."\n", $message); - } -} diff --git a/tests/Monolog/Handler/AbstractHandlerTest.php b/tests/Monolog/Handler/AbstractHandlerTest.php new file mode 100644 index 0000000..560ce99 --- /dev/null +++ b/tests/Monolog/Handler/AbstractHandlerTest.php @@ -0,0 +1,54 @@ +<?php + +/* + * This file is part of the Monolog package. + * + * (c) Jordi Boggiano <j.boggiano@seld.be> + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Monolog\Handler; + +use Monolog\Logger; + +class AbstractHandlerTest extends \PHPUnit_Framework_TestCase +{ + public function testHandle() + { + $handler = new TestHandler(); + $this->assertTrue($handler->handle($this->getMessage())); + } + + public function testHandleLowerLevelMessage() + { + $handler = new TestHandler(); + $this->assertFalse($handler->handle($this->getMessage(Logger::DEBUG))); + } + + public function testHandleBubbling() + { + $handler = new TestHandler(Logger::DEBUG, true); + $this->assertFalse($handler->handle($this->getMessage())); + } + + protected function getMessage($level = Logger::WARNING) + { + return array( + 'level' => $level, + 'level_name' => 'WARNING', + 'channel' => 'log', + 'message' => 'foo', + 'datetime' => new \DateTime, + 'extra' => array(), + ); + } +} + +class TestHandler extends AbstractHandler +{ + public function write($message) + { + } +}
\ No newline at end of file diff --git a/tests/Monolog/Handler/NullHandlerTest.php b/tests/Monolog/Handler/NullHandlerTest.php new file mode 100644 index 0000000..6e3837f --- /dev/null +++ b/tests/Monolog/Handler/NullHandlerTest.php @@ -0,0 +1,51 @@ +<?php + +/* + * This file is part of the Monolog package. + * + * (c) Jordi Boggiano <j.boggiano@seld.be> + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Monolog\Handler; + +use Monolog\Logger; + +class NullHandlerTest extends \PHPUnit_Framework_TestCase +{ + public function testHandle() + { + $handler = new NullHandler(); + $this->assertTrue($handler->handle($this->getMessage())); + } + + public function testHandleLowerLevelMessage() + { + $handler = new NullHandler(Logger::WARNING); + $this->assertFalse($handler->handle($this->getMessage(Logger::DEBUG))); + } + + public function testHandleBubbling() + { + $handler = new NullHandler(Logger::DEBUG, true); + $this->assertFalse($handler->handle($this->getMessage())); + } + + /** + * No-op test for coverage + */ + public function testWrite() + { + $handler = new NullHandler(); + $handler->write($this->getMessage()); + } + + protected function getMessage($level = Logger::WARNING) + { + return array( + 'level' => $level, + ); + } +}
\ No newline at end of file diff --git a/tests/Monolog/Handler/StreamHandlerTest.php b/tests/Monolog/Handler/StreamHandlerTest.php new file mode 100644 index 0000000..58ff92e --- /dev/null +++ b/tests/Monolog/Handler/StreamHandlerTest.php @@ -0,0 +1,61 @@ +<?php + +/* + * This file is part of the Monolog package. + * + * (c) Jordi Boggiano <j.boggiano@seld.be> + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Monolog\Handler; + +use Monolog\Logger; + +class StreamHandlerTest extends \PHPUnit_Framework_TestCase +{ + public function testWrite() + { + $handle = fopen('php://memory', 'a+'); + $handler = new StreamHandler($handle); + $handler->write(array('message' => 'test')); + $handler->write(array('message' => 'test2')); + $handler->write(array('message' => 'test3')); + fseek($handle, 0); + $this->assertEquals('testtest2test3', fread($handle, 100)); + } + + public function testClose() + { + $handle = fopen('php://memory', 'a+'); + $handler = new StreamHandler($handle); + $this->assertTrue(is_resource($handle)); + $handler->close(); + $this->assertFalse(is_resource($handle)); + } + + public function testWriteCreatesTheStreamResource() + { + $handler = new StreamHandler('php://memory'); + $handler->write(array('message' => 'test')); + } + + /** + * @expectedException LogicException + */ + public function testWriteMissingResource() + { + $handler = new StreamHandler(null); + $handler->write(array('message' => 'test')); + } + + /** + * @expectedException UnexpectedValueException + */ + public function testWriteInvalidResource() + { + $handler = new StreamHandler('bogus://url'); + @$handler->write(array('message' => 'test')); + } +} diff --git a/tests/Monolog/LogTest.php b/tests/Monolog/LogTest.php deleted file mode 100644 index 0a9e87d..0000000 --- a/tests/Monolog/LogTest.php +++ /dev/null @@ -1,44 +0,0 @@ -<?php - -/* - * This file is part of the Monolog package. - * - * (c) Jordi Boggiano <j.boggiano@seld.be> - * - * For the full copyright and license information, please view the LICENSE - * file that was distributed with this source code. - */ - -namespace Monolog; - -class LogTest extends \PHPUnit_Framework_TestCase -{ - public function testLog() - { - $logger = new Log('bob'); - $writer1 = $this->getMock('Monolog\Writer\NullWriter', array('write')); - $writer1->expects($this->once()) - ->method('write') - ->with('bob', Logger::WARNING, 'test'); - $writer2 = $this->getMock('Monolog\Writer\NullWriter', array('write')); - $writer2->expects($this->once()) - ->method('write') - ->with('bob', Logger::WARNING, 'test'); - $logger->addWriter($writer1); - $logger->addWriter($writer2); - $logger->addMessage(Logger::WARNING, 'test'); - } - - public function testLogLowLevel() - { - $logger = new Log('bob'); - $logger->setLevel(Logger::ERROR); - $this->assertEquals(Logger::ERROR, $logger->getLevel()); - - $writer1 = $this->getMock('Monolog\Writer\NullWriter', array('write')); - $writer1->expects($this->never()) - ->method('write'); - $logger->addWriter($writer1); - $logger->addMessage(Logger::WARNING, 'test'); - } -} diff --git a/tests/Monolog/LoggerTest.php b/tests/Monolog/LoggerTest.php index ea65e64..c73ab9e 100644 --- a/tests/Monolog/LoggerTest.php +++ b/tests/Monolog/LoggerTest.php @@ -13,33 +13,57 @@ namespace Monolog; class LoggerTest extends \PHPUnit_Framework_TestCase { - public function testLogAll() + public function testLog() { - $logger = new Logger(); - $log1 = $this->getMock('Monolog\Log', array('log'), array('a')); - $log1->expects($this->once()) - ->method('log'); - $log2 = $this->getMock('Monolog\Log', array('log'), array('b')); - $log2->expects($this->once()) - ->method('log'); - $logger->addLog($log1); - $logger->addLog($log2); - $logger->warn('test'); + $logger = new Logger(__METHOD__); + + $handler = $this->getMock('Monolog\Handler\NullHandler', array('handle')); + $handler->expects($this->once()) + ->method('handle'); + $logger->pushHandler($handler); + + $logger->addWarning('test'); } - public function testLogFiltered() + /** + * @dataProvider logValues + */ + public function testLogUntilHandled($bubble) { - $logger = new Logger(); - $log1 = $this->getMock('Monolog\Log', array('log'), array('a')); - $log1->expects($this->exactly(2)) - ->method('log'); - $log2 = $this->getMock('Monolog\Log', array('log'), array('b')); - $log2->expects($this->never()) - ->method('log'); - $logger->addLog($log1); - $logger->addLog($log2); - - $logger->warn('test', 'a'); - $logger->warn('test', array('a')); + $logger = new Logger(__METHOD__); + + $bottomHandler = $this->getMock('Monolog\Handler\NullHandler', array('handle')); + $bottomHandler->expects($bubble ? $this->once() : $this->never()) + ->method('handle'); + $logger->pushHandler($bottomHandler); + + $topHandler = $this->getMock('Monolog\Handler\NullHandler', array('handle')); + $topHandler->expects($this->once()) + ->method('handle') + ->will($this->returnValue(!$bubble)); + $logger->pushHandler($topHandler); + + $logger->addWarning('test'); + } + + public function logValues() + { + return array(array(true), array(false)); + } + + public function testPushPopHandler() + { + $logger = new Logger(__METHOD__); + $handler1 = $this->getMock('Monolog\Handler\NullHandler', array('handle')); + $handler2 = $this->getMock('Monolog\Handler\NullHandler', array('handle')); + $handler3 = $this->getMock('Monolog\Handler\NullHandler', array('handle')); + + $logger->pushHandler($handler1); + $logger->pushHandler($handler2); + $logger->pushHandler($handler3); + + $this->assertEquals($handler3, $logger->popHandler()); + $this->assertEquals($handler2, $logger->popHandler()); + $this->assertEquals($handler1, $logger->popHandler()); } } diff --git a/tests/Monolog/Writer/StreamWriterTest.php b/tests/Monolog/Writer/StreamWriterTest.php deleted file mode 100644 index 2cb88bf..0000000 --- a/tests/Monolog/Writer/StreamWriterTest.php +++ /dev/null @@ -1,37 +0,0 @@ -<?php - -/* - * This file is part of the Monolog package. - * - * (c) Jordi Boggiano <j.boggiano@seld.be> - * - * For the full copyright and license information, please view the LICENSE - * file that was distributed with this source code. - */ - -namespace Monolog\Writer; - -use Monolog\Logger; - -class StreamWritterTest extends \PHPUnit_Framework_TestCase -{ - public function testWrite() - { - $handle = fopen('php://memory', 'a+'); - $writer = new StreamWriter($handle); - $writer->write('log', array('level' => Logger::WARNING, 'message' => 'test')); - $writer->write('log', array('level' => Logger::WARNING, 'message' => 'test2')); - $writer->write('log', array('level' => Logger::WARNING, 'message' => 'test3')); - fseek($handle, 0); - $this->assertEquals('testtest2test3', fread($handle, 100)); - } - - public function testClose() - { - $handle = fopen('php://memory', 'a+'); - $writer = new StreamWriter($handle); - $this->assertTrue(is_resource($handle)); - $writer->close(); - $this->assertFalse(is_resource($handle)); - } -} |