diff --git a/bundled-libs/autoload.php b/bundled-libs/autoload.php index 032b99b4..2d714c76 100644 --- a/bundled-libs/autoload.php +++ b/bundled-libs/autoload.php @@ -4,4 +4,4 @@ require_once __DIR__ . '/composer' . '/autoload_real.php'; -return ComposerAutoloaderInit3146f05565d9c8136a7e59e2a511ce14::getLoader(); +return ComposerAutoloaderInitcbda25b16bb8365467298ce193f0f30c::getLoader(); diff --git a/bundled-libs/composer/autoload_classmap.php b/bundled-libs/composer/autoload_classmap.php index af4ad580..0c90478f 100644 --- a/bundled-libs/composer/autoload_classmap.php +++ b/bundled-libs/composer/autoload_classmap.php @@ -6,4 +6,5 @@ $vendorDir = dirname(dirname(__FILE__)); $baseDir = dirname($vendorDir); return array( + 'Katzgrau\\KLogger\\Logger' => $vendorDir . '/katzgrau/klogger/src/Logger.php', ); diff --git a/bundled-libs/composer/autoload_namespaces.php b/bundled-libs/composer/autoload_namespaces.php index 7993c3ed..8438e130 100644 --- a/bundled-libs/composer/autoload_namespaces.php +++ b/bundled-libs/composer/autoload_namespaces.php @@ -7,4 +7,5 @@ $baseDir = dirname($vendorDir); return array( 'Zend\\Db\\' => array($vendorDir . '/zendframework/zend-db'), + 'Psr\\Log\\' => array($vendorDir . '/psr/log'), ); diff --git a/bundled-libs/composer/autoload_real.php b/bundled-libs/composer/autoload_real.php index f7a1be76..43e74765 100644 --- a/bundled-libs/composer/autoload_real.php +++ b/bundled-libs/composer/autoload_real.php @@ -2,7 +2,7 @@ // autoload_real.php generated by Composer -class ComposerAutoloaderInit3146f05565d9c8136a7e59e2a511ce14 +class ComposerAutoloaderInitcbda25b16bb8365467298ce193f0f30c { private static $loader; @@ -19,9 +19,9 @@ class ComposerAutoloaderInit3146f05565d9c8136a7e59e2a511ce14 return self::$loader; } - spl_autoload_register(array('ComposerAutoloaderInit3146f05565d9c8136a7e59e2a511ce14', 'loadClassLoader'), true, true); + spl_autoload_register(array('ComposerAutoloaderInitcbda25b16bb8365467298ce193f0f30c', 'loadClassLoader'), true, true); self::$loader = $loader = new \Composer\Autoload\ClassLoader(); - spl_autoload_unregister(array('ComposerAutoloaderInit3146f05565d9c8136a7e59e2a511ce14', 'loadClassLoader')); + spl_autoload_unregister(array('ComposerAutoloaderInitcbda25b16bb8365467298ce193f0f30c', 'loadClassLoader')); $vendorDir = dirname(__DIR__); $baseDir = dirname($vendorDir); diff --git a/bundled-libs/composer/installed.json b/bundled-libs/composer/installed.json index 50904c9b..db5a7802 100644 --- a/bundled-libs/composer/installed.json +++ b/bundled-libs/composer/installed.json @@ -46,5 +46,99 @@ "support": { "source": "https://github.com/zendframework/Component_ZendDb/tree/release-2.2.2" } + }, + { + "name": "psr/log", + "version": "1.0.0", + "version_normalized": "1.0.0.0", + "source": { + "type": "git", + "url": "https://github.com/php-fig/log.git", + "reference": "fe0936ee26643249e916849d48e3a51d5f5e278b" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/php-fig/log/zipball/fe0936ee26643249e916849d48e3a51d5f5e278b", + "reference": "fe0936ee26643249e916849d48e3a51d5f5e278b", + "shasum": "" + }, + "time": "2012-12-21 11:40:51", + "type": "library", + "installation-source": "dist", + "autoload": { + "psr-0": { + "Psr\\Log\\": "" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "PHP-FIG", + "homepage": "http://www.php-fig.org/" + } + ], + "description": "Common interface for logging libraries", + "keywords": [ + "log", + "psr", + "psr-3" + ] + }, + { + "name": "katzgrau/klogger", + "version": "1.0.0", + "version_normalized": "1.0.0.0", + "source": { + "type": "git", + "url": "https://github.com/katzgrau/klogger.git", + "reference": "46cdd92a9b4a8443120cc955bf831450cb274813" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/katzgrau/klogger/zipball/46cdd92a9b4a8443120cc955bf831450cb274813", + "reference": "46cdd92a9b4a8443120cc955bf831450cb274813", + "shasum": "" + }, + "require": { + "php": ">=5.3", + "psr/log": "1.0.0" + }, + "require-dev": { + "phpunit/phpunit": "4.0.*" + }, + "time": "2014-03-20 02:36:36", + "type": "library", + "installation-source": "dist", + "autoload": { + "psr-4": { + "Katzgrau\\KLogger\\": "src/" + }, + "classmap": [ + "src/" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Dan Horrigan", + "email": "dan@dhorrigan.com", + "homepage": "http://dhorrigan.com", + "role": "Lead Developer" + }, + { + "name": "Kenny Katzgrau", + "email": "katzgrau@gmail.com" + } + ], + "description": "A Simple Logging Class", + "keywords": [ + "logging" + ] } ] diff --git a/bundled-libs/katzgrau/klogger/.gitignore b/bundled-libs/katzgrau/klogger/.gitignore new file mode 100644 index 00000000..b8128aad --- /dev/null +++ b/bundled-libs/katzgrau/klogger/.gitignore @@ -0,0 +1,3 @@ +/tests/logs/*.txt +/vendor/ +composer.lock \ No newline at end of file diff --git a/bundled-libs/katzgrau/klogger/README.markdown b/bundled-libs/katzgrau/klogger/README.markdown new file mode 100644 index 00000000..b9fa1206 --- /dev/null +++ b/bundled-libs/katzgrau/klogger/README.markdown @@ -0,0 +1,163 @@ +# KLogger: Simple Logging for PHP + +A project written by [Kenny Katzgrau](http://twitter.com/katzgrau) and [Dan Horrigan](http://twitter.com/dhrrgn). + +## About + +KLogger is an easy-to-use [PSR-3](https://github.com/php-fig/fig-standards/blob/master/accepted/PSR-3-logger-interface.md) +compliant logging class for PHP. It isn't naive about +file permissions (which is expected). It was meant to be a class that you could +quickly include into a project and have working right away. + +## Installation + +### Composer + +From the Command Line: + +``` +composer require katzgrau/klogger:1.0.* +``` + +In your `composer.json`: + +``` json +{ + "require": { + "katzgrau/klogger": "1.0.*" + } +} +``` + +## Basic Usage + +``` php + 'Kenny Katzgrau', + 'username' => 'katzgrau', + ], + [ + 'name' => 'Dan Horrigan', + 'username' => 'dhrrgn', + ], +]; + +$logger = new Katzgrau\KLogger\Logger(__DIR__.'/logs'); +$logger->info('Returned a million search results'); +$logger->error('Oh dear.'); +$logger->debug('Got these users from the Database.', $users); +``` + +### Output + +``` +[2014-03-20 3:35:43.762437] [INFO] Returned a million search results +[2014-03-20 3:35:43.762578] [ERROR] Oh dear. +[2014-03-20 3:35:43.762795] [DEBUG] Got these users from the Database. + 0: array( + 'name' => 'Kenny Katzgrau', + 'username' => 'katzgrau', + ) + 1: array( + 'name' => 'Dan Horrigan', + 'username' => 'dhrrgn', + ) +``` + +## PSR-3 Compliant + +KLogger is [PSR-3](https://github.com/php-fig/fig-standards/blob/master/accepted/PSR-3-logger-interface.md) +compliant. This means it implements the `Psr\Log\LoggerInterface`. + +[See Here for the interface definition.](https://github.com/php-fig/fig-standards/blob/master/accepted/PSR-3-logger-interface.md#3-psrlogloggerinterface) + +## Setting the Log Level Threshold + +You can use the `Psr\Log\LogLevel` constants to set Log Level Threshold, so that +any messages below that level, will not be logged. + +### Default Level + +The default level is `DEBUG`, which means everything will be logged. + +### Available Levels + +``` php +error('Uh Oh!'); // Will be logged +$logger->info('Something Happened Here'); // Will be NOT logged +``` + +## Why use KLogger? + +Why not? Just drop it in and go. If it saves you time and does what you need, +go for it! Take a line from the book of our C-code fathers: "`build` upon the +work of others". + +## Who uses KLogger? + +Klogger has been used in projects at: + + * The University of Iowa + * The University of Laverne + * The New Jersey Institute of Technology + * Middlesex Hospital in NJ + +Additionally, it's been used in numerous projects, both commercial and personal. + +## Special Thanks + +Special thanks to all contributors: + +* [Dan Horrigan](http://twitter.com/dhrrgn) +* [Tim Kinnane](http://twitter.com/etherealtim) +* [Brian Fenton](http://github.com/fentie) +* [Cameron Will](https://github.com/cwill747) + +## License + +The MIT License + +Copyright (c) 2008-2014 Kenny Katzgrau + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/bundled-libs/katzgrau/klogger/composer.json b/bundled-libs/katzgrau/klogger/composer.json new file mode 100644 index 00000000..335149f1 --- /dev/null +++ b/bundled-libs/katzgrau/klogger/composer.json @@ -0,0 +1,30 @@ +{ + "name": "katzgrau/klogger", + "version": "1.0.0", + "description": "A Simple Logging Class", + "keywords": ["logging"], + "require": { + "php": ">=5.3", + "psr/log": "1.0.0" + }, + "require-dev": { + "phpunit/phpunit": "4.0.*" + }, + "license": "MIT", + "authors": [ + { + "name": "Kenny Katzgrau", + "email": "katzgrau@gmail.com" + }, + { + "name": "Dan Horrigan", + "email": "dan@dhorrigan.com" + } + ], + "autoload": { + "psr-4": { + "Katzgrau\\KLogger\\": "src/" + }, + "classmap": ["src/"] + } +} diff --git a/bundled-libs/katzgrau/klogger/phpunit.xml b/bundled-libs/katzgrau/klogger/phpunit.xml new file mode 100644 index 00000000..3a470a09 --- /dev/null +++ b/bundled-libs/katzgrau/klogger/phpunit.xml @@ -0,0 +1,18 @@ + + + + + tests + + + + + ./vendor + + + diff --git a/bundled-libs/katzgrau/klogger/src/Logger.php b/bundled-libs/katzgrau/klogger/src/Logger.php new file mode 100755 index 00000000..c558f4c0 --- /dev/null +++ b/bundled-libs/katzgrau/klogger/src/Logger.php @@ -0,0 +1,231 @@ +info('Returned a million search results'); //Prints to the log file + * $log->error('Oh dear.'); //Prints to the log file + * $log->debug('x = 5'); //Prints nothing due to current severity threshhold + * + * @author Kenny Katzgrau + * @since July 26, 2008 — Last update July 1, 2012 + * @link http://codefury.net + * @version 0.2.0 + */ + +/** + * Class documentation + */ +class Logger extends AbstractLogger +{ + /** + * Path to the log file + * @var string + */ + private $logFilePath = null; + + /** + * Current minimum logging threshold + * @var integer + */ + private $logLevelThreshold = LogLevel::DEBUG; + + private $logLevels = array( + LogLevel::EMERGENCY => 0, + LogLevel::ALERT => 1, + LogLevel::CRITICAL => 2, + LogLevel::ERROR => 3, + LogLevel::WARNING => 4, + LogLevel::NOTICE => 5, + LogLevel::INFO => 6, + LogLevel::DEBUG => 7, + ); + + /** + * This holds the file handle for this instance's log file + * @var resource + */ + private $fileHandle = null; + + /** + * Valid PHP date() format string for log timestamps + * @var string + */ + private $dateFormat = 'Y-m-d G:i:s.u'; + + /** + * Octal notation for default permissions of the log file + * @var integer + */ + private $defaultPermissions = 0777; + + /** + * Class constructor + * + * @param string $logDirectory File path to the logging directory + * @param integer $logLevelThreshold The LogLevel Threshold + * @return void + */ + public function __construct($logDirectory, $logLevelThreshold = LogLevel::DEBUG) + { + $this->logLevelThreshold = $logLevelThreshold; + + $logDirectory = rtrim($logDirectory, '\\/'); + if (! file_exists($logDirectory)) { + mkdir($logDirectory, $this->defaultPermissions, true); + } + + $this->logFilePath = $logDirectory.DIRECTORY_SEPARATOR.'log_'.date('Y-m-d').'.txt'; + if (file_exists($this->logFilePath) && !is_writable($this->logFilePath)) { + throw new RuntimeException('The file could not be written to. Check that appropriate permissions have been set.'); + } + + $this->fileHandle = fopen($this->logFilePath, 'a'); + if ( ! $this->fileHandle) { + throw new RuntimeException('The file could not be opened. Check permissions.'); + } + } + + /** + * Class destructor + */ + public function __destruct() + { + if ($this->fileHandle) { + fclose($this->fileHandle); + } + } + + /** + * Sets the date format used by all instances of KLogger + * + * @param string $dateFormat Valid format string for date() + */ + public function setDateFormat($dateFormat) + { + $this->dateFormat = $dateFormat; + } + + /** + * Sets the Log Level Threshold + * + * @param string $dateFormat Valid format string for date() + */ + public function setLogLevelThreshold($logLevelThreshold) + { + $this->logLevelThreshold = $logLevelThreshold; + } + + /** + * Logs with an arbitrary level. + * + * @param mixed $level + * @param string $message + * @param array $context + * @return null + */ + public function log($level, $message, array $context = array()) + { + if ($this->logLevels[$this->logLevelThreshold] < $this->logLevels[$level]) { + return; + } + $message = $this->formatMessage($level, $message, $context); + $this->write($message); + } + + /** + * Writes a line to the log without prepending a status or timestamp + * + * @param string $line Line to write to the log + * @return void + */ + public function write($message) + { + if (! is_null($this->fileHandle)) { + if (fwrite($this->fileHandle, $message) === false) { + throw new RuntimeException('The file could not be written to. Check that appropriate permissions have been set.'); + } + } + } + + /** + * Formats the message for logging. + * + * @param string $level The Log Level of the message + * @param string $message The message to log + * @param array $context The context + * @return string + */ + private function formatMessage($level, $message, $context) + { + $level = strtoupper($level); + if (! empty($context)) { + $message .= PHP_EOL.$this->indent($this->contextToString($context)); + } + return "[{$this->getTimestamp()}] [{$level}] {$message}".PHP_EOL; + } + + /** + * Gets the correctly formatted Date/Time for the log entry. + * + * PHP DateTime is dump, and you have to resort to trickery to get microseconds + * to work correctly, so here it is. + * + * @return string + */ + private function getTimestamp() + { + $originalTime = microtime(true); + $micro = sprintf("%06d", ($originalTime - floor($originalTime)) * 1000000); + $date = new DateTime(date('Y-m-d H:i:s.'.$micro, $originalTime)); + + return $date->format($this->dateFormat); + } + + /** + * Takes the given context and coverts it to a string. + * + * @param array $context The Context + * @return string + */ + private function contextToString($context) + { + $export = ''; + foreach ($context as $key => $value) { + $export .= "{$key}: "; + $export .= preg_replace(array( + '/=>\s+([a-zA-Z])/im', + '/array\(\s+\)/im', + '/^ |\G /m', + ), array( + '=> $1', + 'array()', + ' ', + ), str_replace('array (', 'array(', var_export($value, true))); + $export .= PHP_EOL; + } + return str_replace(array('\\\\', '\\\''), array('\\', '\''), rtrim($export)); + } + + /** + * Indents the given string with the given indent. + * + * @param string $string The string to indent + * @param string $indent What to use as the indent. + * @return string + */ + private function indent($string, $indent = ' ') + { + return $indent.str_replace("\n", "\n".$indent, $string); + } +} diff --git a/bundled-libs/katzgrau/klogger/tests/LoggerTest.php b/bundled-libs/katzgrau/klogger/tests/LoggerTest.php new file mode 100644 index 00000000..ebe65d83 --- /dev/null +++ b/bundled-libs/katzgrau/klogger/tests/LoggerTest.php @@ -0,0 +1,20 @@ +logPath = __DIR__.'/logs'; + $this->logger = new Logger($this->logPath); + } + + public function testImplementsPsr3LoggerInterface() + { + $this->assertInstanceOf('Psr\Log\LoggerInterface', $this->logger); + } +} diff --git a/bundled-libs/katzgrau/klogger/tests/logs/.gitkeep b/bundled-libs/katzgrau/klogger/tests/logs/.gitkeep new file mode 100644 index 00000000..e69de29b diff --git a/bundled-libs/psr/log/.gitignore b/bundled-libs/psr/log/.gitignore new file mode 100644 index 00000000..22d0d82f --- /dev/null +++ b/bundled-libs/psr/log/.gitignore @@ -0,0 +1 @@ +vendor diff --git a/bundled-libs/psr/log/LICENSE b/bundled-libs/psr/log/LICENSE new file mode 100644 index 00000000..474c952b --- /dev/null +++ b/bundled-libs/psr/log/LICENSE @@ -0,0 +1,19 @@ +Copyright (c) 2012 PHP Framework Interoperability Group + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/bundled-libs/psr/log/Psr/Log/AbstractLogger.php b/bundled-libs/psr/log/Psr/Log/AbstractLogger.php new file mode 100644 index 00000000..00f90345 --- /dev/null +++ b/bundled-libs/psr/log/Psr/Log/AbstractLogger.php @@ -0,0 +1,120 @@ +log(LogLevel::EMERGENCY, $message, $context); + } + + /** + * Action must be taken immediately. + * + * Example: Entire website down, database unavailable, etc. This should + * trigger the SMS alerts and wake you up. + * + * @param string $message + * @param array $context + * @return null + */ + public function alert($message, array $context = array()) + { + $this->log(LogLevel::ALERT, $message, $context); + } + + /** + * Critical conditions. + * + * Example: Application component unavailable, unexpected exception. + * + * @param string $message + * @param array $context + * @return null + */ + public function critical($message, array $context = array()) + { + $this->log(LogLevel::CRITICAL, $message, $context); + } + + /** + * Runtime errors that do not require immediate action but should typically + * be logged and monitored. + * + * @param string $message + * @param array $context + * @return null + */ + public function error($message, array $context = array()) + { + $this->log(LogLevel::ERROR, $message, $context); + } + + /** + * Exceptional occurrences that are not errors. + * + * Example: Use of deprecated APIs, poor use of an API, undesirable things + * that are not necessarily wrong. + * + * @param string $message + * @param array $context + * @return null + */ + public function warning($message, array $context = array()) + { + $this->log(LogLevel::WARNING, $message, $context); + } + + /** + * Normal but significant events. + * + * @param string $message + * @param array $context + * @return null + */ + public function notice($message, array $context = array()) + { + $this->log(LogLevel::NOTICE, $message, $context); + } + + /** + * Interesting events. + * + * Example: User logs in, SQL logs. + * + * @param string $message + * @param array $context + * @return null + */ + public function info($message, array $context = array()) + { + $this->log(LogLevel::INFO, $message, $context); + } + + /** + * Detailed debug information. + * + * @param string $message + * @param array $context + * @return null + */ + public function debug($message, array $context = array()) + { + $this->log(LogLevel::DEBUG, $message, $context); + } +} diff --git a/bundled-libs/psr/log/Psr/Log/InvalidArgumentException.php b/bundled-libs/psr/log/Psr/Log/InvalidArgumentException.php new file mode 100644 index 00000000..67f852d1 --- /dev/null +++ b/bundled-libs/psr/log/Psr/Log/InvalidArgumentException.php @@ -0,0 +1,7 @@ +logger = $logger; + } +} diff --git a/bundled-libs/psr/log/Psr/Log/LoggerInterface.php b/bundled-libs/psr/log/Psr/Log/LoggerInterface.php new file mode 100644 index 00000000..476bb962 --- /dev/null +++ b/bundled-libs/psr/log/Psr/Log/LoggerInterface.php @@ -0,0 +1,114 @@ +log(LogLevel::EMERGENCY, $message, $context); + } + + /** + * Action must be taken immediately. + * + * Example: Entire website down, database unavailable, etc. This should + * trigger the SMS alerts and wake you up. + * + * @param string $message + * @param array $context + * @return null + */ + public function alert($message, array $context = array()) + { + $this->log(LogLevel::ALERT, $message, $context); + } + + /** + * Critical conditions. + * + * Example: Application component unavailable, unexpected exception. + * + * @param string $message + * @param array $context + * @return null + */ + public function critical($message, array $context = array()) + { + $this->log(LogLevel::CRITICAL, $message, $context); + } + + /** + * Runtime errors that do not require immediate action but should typically + * be logged and monitored. + * + * @param string $message + * @param array $context + * @return null + */ + public function error($message, array $context = array()) + { + $this->log(LogLevel::ERROR, $message, $context); + } + + /** + * Exceptional occurrences that are not errors. + * + * Example: Use of deprecated APIs, poor use of an API, undesirable things + * that are not necessarily wrong. + * + * @param string $message + * @param array $context + * @return null + */ + public function warning($message, array $context = array()) + { + $this->log(LogLevel::WARNING, $message, $context); + } + + /** + * Normal but significant events. + * + * @param string $message + * @param array $context + * @return null + */ + public function notice($message, array $context = array()) + { + $this->log(LogLevel::NOTICE, $message, $context); + } + + /** + * Interesting events. + * + * Example: User logs in, SQL logs. + * + * @param string $message + * @param array $context + * @return null + */ + public function info($message, array $context = array()) + { + $this->log(LogLevel::INFO, $message, $context); + } + + /** + * Detailed debug information. + * + * @param string $message + * @param array $context + * @return null + */ + public function debug($message, array $context = array()) + { + $this->log(LogLevel::DEBUG, $message, $context); + } + + /** + * Logs with an arbitrary level. + * + * @param mixed $level + * @param string $message + * @param array $context + * @return null + */ + abstract public function log($level, $message, array $context = array()); +} diff --git a/bundled-libs/psr/log/Psr/Log/NullLogger.php b/bundled-libs/psr/log/Psr/Log/NullLogger.php new file mode 100644 index 00000000..553a3c59 --- /dev/null +++ b/bundled-libs/psr/log/Psr/Log/NullLogger.php @@ -0,0 +1,27 @@ +logger) { }` + * blocks. + */ +class NullLogger extends AbstractLogger +{ + /** + * Logs with an arbitrary level. + * + * @param mixed $level + * @param string $message + * @param array $context + * @return null + */ + public function log($level, $message, array $context = array()) + { + // noop + } +} diff --git a/bundled-libs/psr/log/Psr/Log/Test/LoggerInterfaceTest.php b/bundled-libs/psr/log/Psr/Log/Test/LoggerInterfaceTest.php new file mode 100644 index 00000000..a9328151 --- /dev/null +++ b/bundled-libs/psr/log/Psr/Log/Test/LoggerInterfaceTest.php @@ -0,0 +1,116 @@ + " + * + * Example ->error('Foo') would yield "error Foo" + * + * @return string[] + */ + abstract function getLogs(); + + public function testImplements() + { + $this->assertInstanceOf('Psr\Log\LoggerInterface', $this->getLogger()); + } + + /** + * @dataProvider provideLevelsAndMessages + */ + public function testLogsAtAllLevels($level, $message) + { + $logger = $this->getLogger(); + $logger->{$level}($message, array('user' => 'Bob')); + $logger->log($level, $message, array('user' => 'Bob')); + + $expected = array( + $level.' message of level '.$level.' with context: Bob', + $level.' message of level '.$level.' with context: Bob', + ); + $this->assertEquals($expected, $this->getLogs()); + } + + public function provideLevelsAndMessages() + { + return array( + LogLevel::EMERGENCY => array(LogLevel::EMERGENCY, 'message of level emergency with context: {user}'), + LogLevel::ALERT => array(LogLevel::ALERT, 'message of level alert with context: {user}'), + LogLevel::CRITICAL => array(LogLevel::CRITICAL, 'message of level critical with context: {user}'), + LogLevel::ERROR => array(LogLevel::ERROR, 'message of level error with context: {user}'), + LogLevel::WARNING => array(LogLevel::WARNING, 'message of level warning with context: {user}'), + LogLevel::NOTICE => array(LogLevel::NOTICE, 'message of level notice with context: {user}'), + LogLevel::INFO => array(LogLevel::INFO, 'message of level info with context: {user}'), + LogLevel::DEBUG => array(LogLevel::DEBUG, 'message of level debug with context: {user}'), + ); + } + + /** + * @expectedException Psr\Log\InvalidArgumentException + */ + public function testThrowsOnInvalidLevel() + { + $logger = $this->getLogger(); + $logger->log('invalid level', 'Foo'); + } + + public function testContextReplacement() + { + $logger = $this->getLogger(); + $logger->info('{Message {nothing} {user} {foo.bar} a}', array('user' => 'Bob', 'foo.bar' => 'Bar')); + + $expected = array('info {Message {nothing} Bob Bar a}'); + $this->assertEquals($expected, $this->getLogs()); + } + + public function testObjectCastToString() + { + $dummy = $this->getMock('Psr\Log\Test\DummyTest', array('__toString')); + $dummy->expects($this->once()) + ->method('__toString') + ->will($this->returnValue('DUMMY')); + + $this->getLogger()->warning($dummy); + } + + public function testContextCanContainAnything() + { + $context = array( + 'bool' => true, + 'null' => null, + 'string' => 'Foo', + 'int' => 0, + 'float' => 0.5, + 'nested' => array('with object' => new DummyTest), + 'object' => new \DateTime, + 'resource' => fopen('php://memory', 'r'), + ); + + $this->getLogger()->warning('Crazy context data', $context); + } + + public function testContextExceptionKeyCanBeExceptionOrOtherValues() + { + $this->getLogger()->warning('Random message', array('exception' => 'oops')); + $this->getLogger()->critical('Uncaught Exception!', array('exception' => new \LogicException('Fail'))); + } +} + +class DummyTest +{ +} \ No newline at end of file diff --git a/bundled-libs/psr/log/README.md b/bundled-libs/psr/log/README.md new file mode 100644 index 00000000..574bc1cb --- /dev/null +++ b/bundled-libs/psr/log/README.md @@ -0,0 +1,45 @@ +PSR Log +======= + +This repository holds all interfaces/classes/traits related to +[PSR-3](https://github.com/php-fig/fig-standards/blob/master/accepted/PSR-3-logger-interface.md). + +Note that this is not a logger of its own. It is merely an interface that +describes a logger. See the specification for more details. + +Usage +----- + +If you need a logger, you can use the interface like this: + +```php +logger = $logger; + } + + public function doSomething() + { + if ($this->logger) { + $this->logger->info('Doing work'); + } + + // do something useful + } +} +``` + +You can then pick one of the implementations of the interface to get a logger. + +If you want to implement the interface, you can require this package and +implement `Psr\Log\LoggerInterface` in your code. Please read the +[specification text](https://github.com/php-fig/fig-standards/blob/master/accepted/PSR-3-logger-interface.md) +for details. diff --git a/bundled-libs/psr/log/composer.json b/bundled-libs/psr/log/composer.json new file mode 100644 index 00000000..6bdcc219 --- /dev/null +++ b/bundled-libs/psr/log/composer.json @@ -0,0 +1,17 @@ +{ + "name": "psr/log", + "description": "Common interface for logging libraries", + "keywords": ["psr", "psr-3", "log"], + "license": "MIT", + "authors": [ + { + "name": "PHP-FIG", + "homepage": "http://www.php-fig.org/" + } + ], + "autoload": { + "psr-0": { + "Psr\\Log\\": "" + } + } +} diff --git a/composer.json b/composer.json index 3ba8394a..8b994d3f 100644 --- a/composer.json +++ b/composer.json @@ -7,8 +7,9 @@ ], "require": { "php": ">=5.3.3", - "zendframework/zend-db": "2.*" - } + "zendframework/zend-db": "2.*", + "katzgrau/klogger": "1.0.*" + }, "config": { "vendor-dir": "bundled-libs" } diff --git a/docs/NEWS b/docs/NEWS index c73f7541..dc0c55fd 100644 --- a/docs/NEWS +++ b/docs/NEWS @@ -3,7 +3,9 @@ Version 2.0-beta2 () ------------------------------------------------------------------------ - + + * Include klogger, call it as $serendipity['logger']->debug/error + * Add HTTP_Request2 and dependencies as bundled libraries and update PEAR library to version 1.9.4 diff --git a/include/functions_trackbacks.inc.php b/include/functions_trackbacks.inc.php index d5d271ad..83b244f2 100644 --- a/include/functions_trackbacks.inc.php +++ b/include/functions_trackbacks.inc.php @@ -668,14 +668,14 @@ function serendipity_handle_references($id, $author, $title, $text, $dry_run = f static $old_references = array(); static $saved_references = array(); static $saved_urls = array(); - static $debug = false; + $serendipity['logger']->debug("serendipity_handle_references"); if ($dry_run) { // Store the current list of references. We might need to restore them for later user. $old_references = serendipity_db_query("SELECT * FROM {$serendipity['dbPrefix']}references WHERE (type = '' OR type IS NULL) AND entry_id = " . (int)$id, false, 'assoc'); - if ($debug && is_string($old_references)) { - echo '' . $old_references . ""; + if (is_string($old_references)) { + $serendipity['logger']->debug($old_references); } if (is_array($old_references) && count($old_references) > 0) { @@ -686,15 +686,14 @@ function serendipity_handle_references($id, $author, $title, $text, $dry_run = f $saved_urls[$old_reference['link']] = true; } } - if ($debug) echo "Got references in dry run:
" . print_r($current_references, true) . "
\n"; + $serendipity['logger']->debug("Got references in dry run: " . print_r($current_references, true)); } else { // A dry-run was called previously and restorable references are found. Restore them now. $del = serendipity_db_query("DELETE FROM {$serendipity['dbPrefix']}references WHERE (type = '' OR type IS NULL) AND entry_id = " . (int)$id); - if ($debug && is_string($del)) { - echo '' . $del . ""; + if (is_string($del)) { + $serendipity['logger']->debug($del); } - - if ($debug) echo "Deleted references."; + $serendipity['logger']->debug("Deleted references"); if (is_array($old_references) && count($old_references) > 0) { $current_references = array(); @@ -703,13 +702,13 @@ function serendipity_handle_references($id, $author, $title, $text, $dry_run = f $current_references[$old_reference['link'] . $old_reference['name']] = $old_reference; $q = serendipity_db_insert('references', $old_reference, 'show'); $cr = serendipity_db_query($q); - if ($debug && is_string($cr)) { - echo '' . $cr . ""; + if (is_string($cr)) { + $serendipity['logger']->debug($cr); } } } - if ($debug) echo "Got references in final run:
" . print_r($current_references, true) . "
\n"; + $serendipity['logger']->debug("Got references in final run:" . print_r($current_references, true)); } if (!preg_match_all('@]+?href\s*=\s*["\']?([^\'" >]+?)[ \'"][^>]*>(.+?)@i', $text, $matches)) { @@ -731,13 +730,13 @@ function serendipity_handle_references($id, $author, $title, $text, $dry_run = f $checked_locations = array(); serendipity_plugin_api::hook_event('backend_trackbacks', $locations); for ($i = 0, $j = count($locations); $i < $j; ++$i) { - if ($debug) echo "Checking {$locations[$i]}..."; + $serendipity['logger']->debug("Checking {$locations[$i]}..."); if ($locations[$i][0] == '/') { $locations[$i] = 'http' . (!empty($_SERVER['HTTPS']) && strtolower($_SERVER['HTTPS']) != 'off' ? 's' : '') . '://' . $_SERVER['HTTP_HOST'] . $locations[$i]; } if (isset($checked_locations[$locations[$i]])) { - if ($debug) echo "Already checked."; + $serendipity['logger']->debug("Already checked"); continue; } @@ -757,42 +756,42 @@ function serendipity_handle_references($id, $author, $title, $text, $dry_run = f AND (type = '' OR type IS NULL)"; $row = serendipity_db_query($query, true, 'num'); - if ($debug && is_string($row)) { - echo '' . $row . ""; + if (is_string($row)) { + $serendipity['logger']->debug($row); } $names[$i] = strip_tags($names[$i]); if (empty($names[$i])) { - if ($debug) echo "Found reference $locations[$i] w/o name. Adding location as name."; + $serendipity['logger']->debug("Found reference $locations[$i] w/o name. Adding location as name"); $names[$i] = $locations[$i]; } if ($row[0] > 0 && isset($saved_references[$locations[$i] . $names[$i]])) { - if ($debug) echo "Found references for $id, skipping rest"; + $serendipity['logger']->debug("Found references for $id, skipping rest"); continue; } if (!isset($serendipity['noautodiscovery']) || !$serendipity['noautodiscovery']) { if (!$dry_run) { if (!isset($saved_urls[$locations[$i]])){ - if ($debug) echo "Enabling autodiscovery."; + $serendipity['logger']->debug("Enabling autodiscovery"); serendipity_reference_autodiscover($locations[$i], $url, $author, $title, serendipity_trackback_excerpt($text)); + } else { + $serendipity['logger']->debug("This reference was already used before in $id and therefore will not be trackbacked again"); } - elseif ($debug) echo "This reference was already used before in $id and therefore will not be trackbacked again."; - } elseif ($debug) { - echo "Dry run: Skipping autodiscovery"; + } else { + $serendipity['logger']->debug("Dry run: Skipping autodiscovery"); } $checked_locations[$locations[$i]] = true; // Store trackbacked link so that no further trackbacks will be sent to the same link - } elseif ($debug) { - echo "Skipping full autodiscovery"; + } else { + $serendipity['logger']->debug("Skipping full autodiscovery"); } } $del = serendipity_db_query("DELETE FROM {$serendipity['dbPrefix']}references WHERE entry_id=" . (int)$id . " AND (type = '' OR type IS NULL)"); - if ($debug && is_string($del)) { - echo '' . $del . ""; + if (is_string($del)) { + $serendipity['logger']->debug($del); } - - if ($debug) echo "Deleted references again."; + $serendipity['logger']->debug("Deleted references again"); if (!is_array($old_references)) { $old_references = array(); @@ -812,16 +811,16 @@ function serendipity_handle_references($id, $author, $title, $text, $dry_run = f $query = "INSERT INTO {$serendipity['dbPrefix']}references (id, entry_id, name, link) VALUES("; $query .= (int)$current_references[$locations[$i] . $names[$i]]['id'] . ", " . (int)$id . ", '" . $i_link . "', '" . $i_location . "')"; $ins = serendipity_db_query($query); - if ($debug && is_string($ins)) { - echo '' . $ins . ""; + if (is_string($ins)) { + $serendipity['logger']->debug($ins); } $duplicate_check[$locations[$i] . $names[$i]] = true; } else { $query = "INSERT INTO {$serendipity['dbPrefix']}references (entry_id, name, link) VALUES("; $query .= (int)$id . ", '" . $i_link . "', '" . $i_location . "')"; $ins = serendipity_db_query($query); - if ($debug && is_string($ins)) { - echo '' . $ins . ""; + if (is_string($ins)) { + $serendipity['logger']->debug($ins); } $old_references[] = array( @@ -833,15 +832,11 @@ function serendipity_handle_references($id, $author, $title, $text, $dry_run = f $duplicate_check[$i_location . $i_link] = true; } - if ($debug) { - echo "Current lookup for {$locations[$i]}{$names[$i]} is
" . print_r($current_references[$locations[$i] . $names[$i]], true) . "
\n"; - echo '' . $query . ""; - } + $serendipity['logger']->debug("Current lookup for {$locations[$i]}{$names[$i]} is" . print_r($current_references[$locations[$i] . $names[$i]], true)); + $serendipity['logger']->debug($query); } - if ($debug) { - echo "Old/Saved locations:
" . print_r($old_references, true) . "
\n"; - } + $serendipity['logger']->debug(print_r($old_references, true)); // Add citations preg_match_all('@]*>([^<]+)@i', $text, $matches); @@ -851,8 +846,8 @@ function serendipity_handle_references($id, $author, $title, $text, $dry_run = f $query .= (int)$id . ", '" . serendipity_db_escape_string($citation) . "')"; $cite = serendipity_db_query($query); - if ($debug && is_string($cite)) { - echo '' . $cite . ""; + if (is_string($cite)) { + $serendipity['logger']->debug($cite); } } } diff --git a/index.php b/index.php index d7336607..5694a8be 100644 --- a/index.php +++ b/index.php @@ -2,19 +2,17 @@ # Copyright (c) 2003-2005, Jannis Hermanns (on behalf the Serendipity Developer Team) # All rights reserved. See LICENSE file for licensing details -$global_debug = false; -if ($global_debug) { - #apd_set_pprof_trace(); +#apd_set_pprof_trace(); - function microtime_float() { - list($usec, $sec) = explode(" ", microtime()); - return ((float)$usec + (float)$sec); - } - - $time_start = microtime_float(); +function microtime_float() { + list($usec, $sec) = explode(" ", microtime()); + return ((float)$usec + (float)$sec); } +$time_start = microtime_float(); + + // We need to set this to return a 200 since we use .htaccess ErrorDocument // rules to handle archives. header('HTTP/1.0 200'); @@ -674,10 +672,6 @@ if (!defined('NO_EXIT')) { $serendipity['smarty']->display(serendipity_getTemplateFile($serendipity['smarty_file'], 'serendipityPath')); } -if ($global_debug) { - /* TODO: Remove (hide) this debug */ - echo '
Page delivered in '. round(microtime_float()-$time_start,6) .' seconds, '. sizeof(get_included_files()) .' files included
'; - echo ''; -} +$serendipity['logger']->debug('Page delivered in '. round(microtime_float()-$time_start,6) .' seconds, '. sizeof(get_included_files()) .' files included'); /* vim: set sts=4 ts=4 expandtab : */ diff --git a/serendipity_config.inc.php b/serendipity_config.inc.php index a84be342..848c830b 100644 --- a/serendipity_config.inc.php +++ b/serendipity_config.inc.php @@ -257,8 +257,13 @@ include($local_config); if ($serendipity['production'] === 'debug') { error_reporting(E_ALL &~E_NOTICE | E_STRICT); + $serendipity['log_level'] = Psr\Log\LogLevel::DEBUG; +} else { + $serendipity['log_level'] = Psr\Log\LogLevel::ERROR; } +$serendipity['logger'] = new Katzgrau\KLogger\Logger($serendipity['serendipityPath'] . '/templates_c/logs', $serendipity['log_level']); + //[internal callback function]: errorToExceptionHandler() if(is_callable($serendipity['errorhandler'], false, $callable_name)) { // set serendipity global error to exeption handler @@ -281,6 +286,7 @@ include(S9Y_INCLUDE_PATH . 'include/functions.inc.php'); if (serendipity_FUNCTIONS_LOADED !== true) { $serendipity['lang'] = 'en'; include(S9Y_INCLUDE_PATH . 'include/lang.inc.php'); + $serendipity['logger']->critical(sprintf(INCLUDE_ERROR . '
' . FILE_CREATE_YOURSELF, 'include/functions.inc.php')); serendipity_die(sprintf(INCLUDE_ERROR . '
' . FILE_CREATE_YOURSELF, 'include/functions.inc.php')); } @@ -290,6 +296,7 @@ if (serendipity_FUNCTIONS_LOADED !== true) { if (!serendipity_db_connect()) { $serendipity['lang'] = 'en'; include(S9Y_INCLUDE_PATH . 'include/lang.inc.php'); + $serendipity['logger']->critical(DATABASE_ERROR); serendipity_die(DATABASE_ERROR); } @@ -429,5 +436,6 @@ if (isset($_SESSION['serendipityUser'])) { if (isset($_SESSION['serendipityEmail'])) { $serendipity['email'] = $_SESSION['serendipityEmail']; } + serendipity_plugin_api::hook_event('frontend_configure', $serendipity); /* vim: set sts=4 ts=4 expandtab : */