Use PSR-3 LoggerInterface to allow custom logging implementations.

Note that all deprecated code will be removed in the near future!
parent 1785d98f
...@@ -6,7 +6,9 @@ Exclamation symbols (:exclamation:) note something of importance e.g. breaking c ...@@ -6,7 +6,9 @@ Exclamation symbols (:exclamation:) note something of importance e.g. breaking c
## [Unreleased] ## [Unreleased]
### Added ### Added
### Changed ### Changed
- `TelegramLog` now adheres to [PSR-3] `LoggerInterface` and allows custom logger implementations.
### Deprecated ### Deprecated
- Old logging that uses Monolog still works but will be removed in the near future. Use `TelegramLog::initialize($logger, $update_logger);` from now on.
### Removed ### Removed
### Fixed ### Fixed
### Security ### Security
...@@ -280,6 +282,7 @@ Exclamation symbols (:exclamation:) note something of importance e.g. breaking c ...@@ -280,6 +282,7 @@ Exclamation symbols (:exclamation:) note something of importance e.g. breaking c
[0.45.0-bc-up-download-directory]: https://github.com/php-telegram-bot/core/wiki/Breaking-backwards-compatibility#up-download-directory [0.45.0-bc-up-download-directory]: https://github.com/php-telegram-bot/core/wiki/Breaking-backwards-compatibility#up-download-directory
[0.44.0-bc-update-content-type]: https://github.com/php-telegram-bot/core/wiki/Breaking-backwards-compatibility#update-getupdatecontent [0.44.0-bc-update-content-type]: https://github.com/php-telegram-bot/core/wiki/Breaking-backwards-compatibility#update-getupdatecontent
[example-bot]: https://github.com/php-telegram-bot/example-bot [example-bot]: https://github.com/php-telegram-bot/example-bot
[PSR-3]: https://www.php-fig.org/psr/psr-3
[Unreleased]: https://github.com/php-telegram-bot/core/compare/master...develop [Unreleased]: https://github.com/php-telegram-bot/core/compare/master...develop
[0.57.0]: https://github.com/php-telegram-bot/core/compare/0.56.0...0.57.0 [0.57.0]: https://github.com/php-telegram-bot/core/compare/0.56.0...0.57.0
......
...@@ -28,6 +28,7 @@ ...@@ -28,6 +28,7 @@
"ext-curl": "*", "ext-curl": "*",
"ext-json": "*", "ext-json": "*",
"ext-mbstring": "*", "ext-mbstring": "*",
"psr/log": "^1.1",
"monolog/monolog": "^1.24", "monolog/monolog": "^1.24",
"guzzlehttp/guzzle": "^6.3" "guzzlehttp/guzzle": "^6.3"
}, },
......
...@@ -4,7 +4,7 @@ ...@@ -4,7 +4,7 @@
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies", "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
"This file is @generated automatically" "This file is @generated automatically"
], ],
"content-hash": "b3ac8abe31dc69491d76f5b4bb65ca26", "content-hash": "07b4a4919442371656638370b1b75f85",
"packages": [ "packages": [
{ {
"name": "guzzlehttp/guzzle", "name": "guzzlehttp/guzzle",
......
...@@ -539,7 +539,7 @@ class Telegram ...@@ -539,7 +539,7 @@ class Telegram
public function enableAdmin($admin_id) public function enableAdmin($admin_id)
{ {
if (!is_int($admin_id) || $admin_id <= 0) { if (!is_int($admin_id) || $admin_id <= 0) {
TelegramLog::error('Invalid value "%s" for admin.', $admin_id); TelegramLog::error('Invalid value "' . $admin_id . '" for admin.');
} elseif (!in_array($admin_id, $this->admins_list, true)) { } elseif (!in_array($admin_id, $this->admins_list, true)) {
$this->admins_list[] = $admin_id; $this->admins_list[] = $admin_id;
} }
...@@ -632,7 +632,7 @@ class Telegram ...@@ -632,7 +632,7 @@ class Telegram
public function addCommandsPath($path, $before = true) public function addCommandsPath($path, $before = true)
{ {
if (!is_dir($path)) { if (!is_dir($path)) {
TelegramLog::error('Commands path "%s" does not exist.', $path); TelegramLog::error('Commands path "' . $path . '" does not exist.');
} elseif (!in_array($path, $this->commands_paths, true)) { } elseif (!in_array($path, $this->commands_paths, true)) {
if ($before) { if ($before) {
array_unshift($this->commands_paths, $path); array_unshift($this->commands_paths, $path);
......
...@@ -10,31 +10,50 @@ ...@@ -10,31 +10,50 @@
namespace Longman\TelegramBot; namespace Longman\TelegramBot;
use Exception;
use Longman\TelegramBot\Exception\TelegramLogException; use Longman\TelegramBot\Exception\TelegramLogException;
use Monolog\Formatter\LineFormatter; use Monolog\Formatter\LineFormatter;
use Monolog\Handler\StreamHandler; use Monolog\Handler\StreamHandler;
use Monolog\Logger; use Monolog\Logger;
use Psr\Log\LoggerInterface;
use Psr\Log\NullLogger;
/**
* Class TelegramLog
*
* @todo Clean out all deprecated code in the near future!
*
* @method static void emergency(string $message, array $context = [])
* @method static void alert(string $message, array $context = [])
* @method static void critical(string $message, array $context = [])
* @method static void error(string $message, array $context = [])
* @method static void warning(string $message, array $context = [])
* @method static void notice(string $message, array $context = [])
* @method static void info(string $message, array $context = [])
* @method static void debug(string $message, array $context = [])
* @method static void update(string $message, array $context = [])
*/
class TelegramLog class TelegramLog
{ {
/** /**
* Monolog instance * Logger instance
* *
* @var \Monolog\Logger * @var LoggerInterface|Logger
*/ */
protected static $monolog; protected static $logger;
/** /**
* Monolog instance for update * Logger instance for update
* *
* @var \Monolog\Logger * @var LoggerInterface|Logger
*/ */
protected static $monolog_update; protected static $update_logger;
/** /**
* Path for error log * Path for error log
* *
* @var string * @var string
* @deprecated
*/ */
protected static $error_log_path; protected static $error_log_path;
...@@ -42,6 +61,7 @@ class TelegramLog ...@@ -42,6 +61,7 @@ class TelegramLog
* Path for debug log * Path for debug log
* *
* @var string * @var string
* @deprecated
*/ */
protected static $debug_log_path; protected static $debug_log_path;
...@@ -49,6 +69,7 @@ class TelegramLog ...@@ -49,6 +69,7 @@ class TelegramLog
* Path for update log * Path for update log
* *
* @var string * @var string
* @deprecated
*/ */
protected static $update_log_path; protected static $update_log_path;
...@@ -60,80 +81,126 @@ class TelegramLog ...@@ -60,80 +81,126 @@ class TelegramLog
protected static $debug_log_temp_stream_handle; protected static $debug_log_temp_stream_handle;
/** /**
* Initialize Monolog Logger instance, optionally passing an existing one * Initialise Logger instance, optionally passing an existing one.
*
* @param \Monolog\Logger
* *
* @return \Monolog\Logger * @param LoggerInterface|null $logger
* @param LoggerInterface|null $update_logger
*/ */
public static function initialize(Logger $external_monolog = null) public static function initialize(LoggerInterface $logger = null, LoggerInterface $update_logger = null)
{ {
if (self::$monolog === null) { // Clearly deprecated code still being executed.
if ($external_monolog !== null) { if ($logger === null) {
self::$monolog = $external_monolog; (defined('PHPUNIT_TESTSUITE') && PHPUNIT_TESTSUITE) || trigger_error('A PSR-3 compatible LoggerInterface object must be provided. Initialise with a preconfigured logger instance.', E_USER_DEPRECATED);
$logger = new Logger('bot_log');
foreach (self::$monolog->getHandlers() as $handler) { } elseif ($logger instanceof Logger) {
if (method_exists($handler, 'getLevel') && $handler->getLevel() === 400) { foreach ($logger->getHandlers() as $handler) {
self::$error_log_path = 'true'; if (method_exists($handler, 'getLevel') && $handler->getLevel() === Logger::ERROR) {
} self::$error_log_path = 'true';
if (method_exists($handler, 'getLevel') && $handler->getLevel() === 100) { }
self::$debug_log_path = 'true'; if (method_exists($handler, 'getLevel') && $handler->getLevel() === Logger::DEBUG) {
} self::$debug_log_path = 'true';
} }
} else {
self::$monolog = new Logger('bot_log');
} }
} }
return self::$monolog; // Fallback to NullLogger.
self::$logger = $logger ?: new NullLogger();
self::$update_logger = $update_logger ?: new NullLogger();
} }
/** /**
* Initialize error log * Initialise error log (deprecated)
* *
* @param string $path * @param string $path
* *
* @return \Monolog\Logger * @return LoggerInterface
* @throws \Longman\TelegramBot\Exception\TelegramLogException * @throws Exception
* @throws \InvalidArgumentException *
* @throws \Exception * @deprecated Initialise a preconfigured logger instance instead.
*/ */
public static function initErrorLog($path) public static function initErrorLog($path)
{ {
(defined('PHPUNIT_TESTSUITE') && PHPUNIT_TESTSUITE) || trigger_error(__METHOD__ . ' is deprecated and will be removed soon. Initialise with a preconfigured logger instance instead using "TelegramLog::initialize($logger)".', E_USER_DEPRECATED);
if ($path === null || $path === '') { if ($path === null || $path === '') {
throw new TelegramLogException('Empty path for error log'); throw new TelegramLogException('Empty path for error log');
} }
self::initialize(); self::initialize();
self::$error_log_path = $path;
return self::$monolog->pushHandler( // Deprecated code used as fallback.
(new StreamHandler(self::$error_log_path, Logger::ERROR)) if (self::$logger instanceof Logger) {
->setFormatter(new LineFormatter(null, null, true)) self::$error_log_path = $path;
);
self::$logger->pushHandler(
(new StreamHandler(self::$error_log_path, Logger::ERROR))
->setFormatter(new LineFormatter(null, null, true))
);
}
return self::$logger;
} }
/** /**
* Initialize debug log * Initialise debug log (deprecated)
* *
* @param string $path * @param string $path
* *
* @return \Monolog\Logger * @return LoggerInterface
* @throws \Longman\TelegramBot\Exception\TelegramLogException * @throws Exception
* @throws \InvalidArgumentException *
* @throws \Exception * @deprecated Initialise a preconfigured logger instance instead.
*/ */
public static function initDebugLog($path) public static function initDebugLog($path)
{ {
(defined('PHPUNIT_TESTSUITE') && PHPUNIT_TESTSUITE) || trigger_error(__METHOD__ . ' is deprecated and will be removed soon. Initialise with a preconfigured logger instance instead using "TelegramLog::initialize($logger)".', E_USER_DEPRECATED);
if ($path === null || $path === '') { if ($path === null || $path === '') {
throw new TelegramLogException('Empty path for debug log'); throw new TelegramLogException('Empty path for debug log');
} }
self::initialize(); self::initialize();
self::$debug_log_path = $path;
return self::$monolog->pushHandler( // Deprecated code used as fallback.
(new StreamHandler(self::$debug_log_path, Logger::DEBUG)) if (self::$logger instanceof Logger) {
->setFormatter(new LineFormatter(null, null, true)) self::$debug_log_path = $path;
);
self::$logger->pushHandler(
(new StreamHandler(self::$debug_log_path, Logger::DEBUG))
->setFormatter(new LineFormatter(null, null, true))
);
}
return self::$logger;
}
/**
* Initialise update log (deprecated)
*
* @param string $path
*
* @return LoggerInterface
* @throws Exception
*
* @deprecated Initialise a preconfigured logger instance instead.
*/
public static function initUpdateLog($path)
{
(defined('PHPUNIT_TESTSUITE') && PHPUNIT_TESTSUITE) || trigger_error(__METHOD__ . ' is deprecated and will be removed soon. Initialise with a preconfigured logger instance instead using "TelegramLog::initialize($logger)".', E_USER_DEPRECATED);
if ($path === null || $path === '') {
throw new TelegramLogException('Empty path for update log');
}
self::$update_log_path = $path;
if (self::$update_logger === null || self::$update_logger instanceof NullLogger) {
self::$update_logger = new Logger('bot_update_log');
self::$update_logger->pushHandler(
(new StreamHandler(self::$update_log_path, Logger::INFO))
->setFormatter(new LineFormatter('%message%' . PHP_EOL))
);
}
return self::$update_logger;
} }
/** /**
...@@ -144,9 +211,6 @@ class TelegramLog ...@@ -144,9 +211,6 @@ class TelegramLog
public static function getDebugLogTempStream() public static function getDebugLogTempStream()
{ {
if (self::$debug_log_temp_stream_handle === null) { if (self::$debug_log_temp_stream_handle === null) {
if (!self::isDebugLogActive()) {
return false;
}
self::$debug_log_temp_stream_handle = fopen('php://temp', 'w+b'); self::$debug_log_temp_stream_handle = fopen('php://temp', 'w+b');
} }
...@@ -162,48 +226,22 @@ class TelegramLog ...@@ -162,48 +226,22 @@ class TelegramLog
{ {
if (is_resource(self::$debug_log_temp_stream_handle)) { if (is_resource(self::$debug_log_temp_stream_handle)) {
rewind(self::$debug_log_temp_stream_handle); rewind(self::$debug_log_temp_stream_handle);
self::debug($message, stream_get_contents(self::$debug_log_temp_stream_handle)); self::debug(sprintf($message, stream_get_contents(self::$debug_log_temp_stream_handle)));
fclose(self::$debug_log_temp_stream_handle); fclose(self::$debug_log_temp_stream_handle);
self::$debug_log_temp_stream_handle = null; self::$debug_log_temp_stream_handle = null;
} }
} }
/**
* Initialize update log
*
* @param string $path
*
* @return \Monolog\Logger
* @throws \Longman\TelegramBot\Exception\TelegramLogException
* @throws \InvalidArgumentException
* @throws \Exception
*/
public static function initUpdateLog($path)
{
if ($path === null || $path === '') {
throw new TelegramLogException('Empty path for update log');
}
self::$update_log_path = $path;
if (self::$monolog_update === null) {
self::$monolog_update = new Logger('bot_update_log');
self::$monolog_update->pushHandler(
(new StreamHandler(self::$update_log_path, Logger::INFO))
->setFormatter(new LineFormatter('%message%' . PHP_EOL))
);
}
return self::$monolog_update;
}
/** /**
* Is error log active * Is error log active
* *
* @return bool * @return bool
*
* @deprecated Initialise a preconfigured logger instance instead.
*/ */
public static function isErrorLogActive() public static function isErrorLogActive()
{ {
(defined('PHPUNIT_TESTSUITE') && PHPUNIT_TESTSUITE) || trigger_error(__METHOD__ . ' is deprecated and will be removed soon. Initialise with a preconfigured logger instance instead using "TelegramLog::initialize($logger)".', E_USER_DEPRECATED);
return self::$error_log_path !== null; return self::$error_log_path !== null;
} }
...@@ -211,9 +249,12 @@ class TelegramLog ...@@ -211,9 +249,12 @@ class TelegramLog
* Is debug log active * Is debug log active
* *
* @return bool * @return bool
*
* @deprecated Initialise a preconfigured logger instance instead.
*/ */
public static function isDebugLogActive() public static function isDebugLogActive()
{ {
(defined('PHPUNIT_TESTSUITE') && PHPUNIT_TESTSUITE) || trigger_error(__METHOD__ . ' is deprecated and will be removed soon. Initialise with a preconfigured logger instance instead using "TelegramLog::initialize($logger)".', E_USER_DEPRECATED);
return self::$debug_log_path !== null; return self::$debug_log_path !== null;
} }
...@@ -221,69 +262,71 @@ class TelegramLog ...@@ -221,69 +262,71 @@ class TelegramLog
* Is update log active * Is update log active
* *
* @return bool * @return bool
*
* @deprecated Initialise a preconfigured logger instance instead.
*/ */
public static function isUpdateLogActive() public static function isUpdateLogActive()
{ {
(defined('PHPUNIT_TESTSUITE') && PHPUNIT_TESTSUITE) || trigger_error(__METHOD__ . ' is deprecated and will be removed soon. Initialise with a preconfigured logger instance instead using "TelegramLog::initialize($logger)".', E_USER_DEPRECATED);
return self::$update_log_path !== null; return self::$update_log_path !== null;
} }
/** /**
* Report error log * Handle any logging method call.
* *
* @param string $text * @param string $name
* @param array $arguments
*/ */
public static function error($text) public static function __callStatic($name, array $arguments)
{ {
if (self::isErrorLogActive()) { // Get the correct logger instance.
$text = self::getLogText($text, func_get_args()); $logger = null;
self::$monolog->error($text); if (in_array($name, ['emergency', 'alert', 'critical', 'error', 'warning', 'notice', 'info', 'debug',], true)) {
$logger = self::$logger;
} elseif ($name === 'update') {
$logger = self::$update_logger;
$name = 'info';
} else {
return;
} }
}
/** self::initialize(self::$logger, self::$update_logger);
* Report debug log
*
* @param string $text
*/
public static function debug($text)
{
if (self::isDebugLogActive()) {
$text = self::getLogText($text, func_get_args());
self::$monolog->debug($text);
}
}
/** // Replace any placeholders from the passed context.
* Report update log if (count($arguments) >= 2) {
* if (is_array($arguments[1])) {
* @param string $text $arguments[0] = self::interpolate($arguments[0], $arguments[1]);
*/ } else {
public static function update($text) // @todo Old parameter passing active, should be removed in the near future.
{ $arguments[0] = vsprintf($arguments[0], array_splice($arguments, 1));
if (self::isUpdateLogActive()) { }
$text = self::getLogText($text, func_get_args());
self::$monolog_update->info($text);
} }
call_user_func_array([$logger, $name], $arguments);
} }
/** /**
* Applies vsprintf to the text if placeholder replacements are passed along. * Interpolates context values into the message placeholders.
*
* @see https://www.php-fig.org/psr/psr-3/#12-message
* *
* @param string $text * @param string $message
* @param array $args * @param array $context
* *
* @return string * @return string
*/ */
protected static function getLogText($text, array $args = []) protected static function interpolate($message, array $context = [])
{ {
// Pop the $text off the array, as it gets passed via func_get_args(). // build a replacement array with braces around the context keys
array_shift($args); $replace = [];
foreach ($context as $key => $val) {
// If no placeholders have been passed, don't parse the text. // check that the value can be casted to string
if (empty($args)) { if (!is_array($val) && (!is_object($val) || method_exists($val, '__toString'))) {
return $text; $replace['{' . $key . '}'] = $val;
}
} }
return vsprintf($text, $args); // interpolate replacement values into the message and return
return strtr($message, $replace);
} }
} }
...@@ -35,8 +35,9 @@ class TelegramLogTest extends TestCase ...@@ -35,8 +35,9 @@ class TelegramLogTest extends TestCase
protected function setUp() protected function setUp()
{ {
// Make sure no monolog instance is set before each test. // Make sure no logger instance is set before each test.
TestHelpers::setStaticProperty('Longman\TelegramBot\TelegramLog', 'monolog', null); TestHelpers::setStaticProperty('Longman\TelegramBot\TelegramLog', 'logger', null);
TestHelpers::setStaticProperty('Longman\TelegramBot\TelegramLog', 'update_logger', null);
} }
protected function tearDown() protected function tearDown()
...@@ -78,12 +79,14 @@ class TelegramLogTest extends TestCase ...@@ -78,12 +79,14 @@ class TelegramLogTest extends TestCase
TelegramLog::initErrorLog($file); TelegramLog::initErrorLog($file);
TelegramLog::error('my error'); TelegramLog::error('my error');
TelegramLog::error('my 50% error'); TelegramLog::error('my 50% error');
TelegramLog::error('my %s error', 'placeholder'); TelegramLog::error('my old %s %s error', 'custom', 'placeholder');
TelegramLog::error('my new {place} {holder} error', ['place' => 'custom', 'holder' => 'placeholder']);
$this->assertFileExists($file); $this->assertFileExists($file);
$error_log = file_get_contents($file); $error_log = file_get_contents($file);
$this->assertContains('bot_log.ERROR: my error', $error_log); $this->assertContains('bot_log.ERROR: my error', $error_log);
$this->assertContains('bot_log.ERROR: my 50% error', $error_log); $this->assertContains('bot_log.ERROR: my 50% error', $error_log);
$this->assertContains('bot_log.ERROR: my placeholder error', $error_log); $this->assertContains('bot_log.ERROR: my old custom placeholder error', $error_log);
$this->assertContains('bot_log.ERROR: my new custom placeholder error', $error_log);
} }
public function testDebugStream() public function testDebugStream()
...@@ -93,12 +96,14 @@ class TelegramLogTest extends TestCase ...@@ -93,12 +96,14 @@ class TelegramLogTest extends TestCase
TelegramLog::initDebugLog($file); TelegramLog::initDebugLog($file);
TelegramLog::debug('my debug'); TelegramLog::debug('my debug');
TelegramLog::debug('my 50% debug'); TelegramLog::debug('my 50% debug');
TelegramLog::debug('my %s debug', 'placeholder'); TelegramLog::debug('my old %s %s debug', 'custom', 'placeholder');
TelegramLog::debug('my new {place} {holder} debug', ['place' => 'custom', 'holder' => 'placeholder']);
$this->assertFileExists($file); $this->assertFileExists($file);
$debug_log = file_get_contents($file); $debug_log = file_get_contents($file);
$this->assertContains('bot_log.DEBUG: my debug', $debug_log); $this->assertContains('bot_log.DEBUG: my debug', $debug_log);
$this->assertContains('bot_log.DEBUG: my 50% debug', $debug_log); $this->assertContains('bot_log.DEBUG: my 50% debug', $debug_log);
$this->assertContains('bot_log.DEBUG: my placeholder debug', $debug_log); $this->assertContains('bot_log.DEBUG: my old custom placeholder debug', $debug_log);
$this->assertContains('bot_log.DEBUG: my new custom placeholder debug', $debug_log);
} }
public function testUpdateStream() public function testUpdateStream()
...@@ -108,12 +113,14 @@ class TelegramLogTest extends TestCase ...@@ -108,12 +113,14 @@ class TelegramLogTest extends TestCase
TelegramLog::initUpdateLog($file); TelegramLog::initUpdateLog($file);
TelegramLog::update('my update'); TelegramLog::update('my update');
TelegramLog::update('my 50% update'); TelegramLog::update('my 50% update');
TelegramLog::update('my %s update', 'placeholder'); TelegramLog::update('my old %s %s update', 'custom', 'placeholder');
TelegramLog::update('my new {place} {holder} update', ['place' => 'custom', 'holder' => 'placeholder']);
$this->assertFileExists($file); $this->assertFileExists($file);
$debug_log = file_get_contents($file); $update_log = file_get_contents($file);
$this->assertContains('my update', $debug_log); $this->assertContains('my update', $update_log);
$this->assertContains('my 50% update', $debug_log); $this->assertContains('my 50% update', $update_log);
$this->assertContains('my placeholder update', $debug_log); $this->assertContains('my old custom placeholder update', $update_log);
$this->assertContains('my new custom placeholder update', $update_log);
} }
public function testExternalStream() public function testExternalStream()
...@@ -121,25 +128,29 @@ class TelegramLogTest extends TestCase ...@@ -121,25 +128,29 @@ class TelegramLogTest extends TestCase
$file = self::$logfiles['external']; $file = self::$logfiles['external'];
$this->assertFileNotExists($file); $this->assertFileNotExists($file);
$external_monolog = new Logger('bot_update_log'); $external_monolog = new Logger('bot_external_log');
$external_monolog->pushHandler(new StreamHandler($file, Logger::ERROR)); $external_monolog->pushHandler(new StreamHandler($file, Logger::ERROR));
$external_monolog->pushHandler(new StreamHandler($file, Logger::DEBUG)); $external_monolog->pushHandler(new StreamHandler($file, Logger::DEBUG));
TelegramLog::initialize($external_monolog); TelegramLog::initialize($external_monolog);
TelegramLog::error('my error'); TelegramLog::error('my error');
TelegramLog::error('my 50% error'); TelegramLog::error('my 50% error');
TelegramLog::error('my %s error', 'placeholder'); TelegramLog::error('my old %s %s error', 'custom', 'placeholder');
TelegramLog::error('my new {place} {holder} error', ['place' => 'custom', 'holder' => 'placeholder']);
TelegramLog::debug('my debug'); TelegramLog::debug('my debug');
TelegramLog::debug('my 50% debug'); TelegramLog::debug('my 50% debug');
TelegramLog::debug('my %s debug', 'placeholder'); TelegramLog::debug('my old %s %s debug', 'custom', 'placeholder');
TelegramLog::debug('my new {place} {holder} debug', ['place' => 'custom', 'holder' => 'placeholder']);
$this->assertFileExists($file); $this->assertFileExists($file);
$file_contents = file_get_contents($file); $file_contents = file_get_contents($file);
$this->assertContains('bot_update_log.ERROR: my error', $file_contents); $this->assertContains('bot_external_log.ERROR: my error', $file_contents);
$this->assertContains('bot_update_log.ERROR: my 50% error', $file_contents); $this->assertContains('bot_external_log.ERROR: my 50% error', $file_contents);
$this->assertContains('bot_update_log.ERROR: my placeholder error', $file_contents); $this->assertContains('bot_external_log.ERROR: my old custom placeholder error', $file_contents);
$this->assertContains('bot_update_log.DEBUG: my debug', $file_contents); $this->assertContains('bot_external_log.ERROR: my new custom placeholder error', $file_contents);
$this->assertContains('bot_update_log.DEBUG: my 50% debug', $file_contents); $this->assertContains('bot_external_log.DEBUG: my debug', $file_contents);
$this->assertContains('bot_update_log.DEBUG: my placeholder debug', $file_contents); $this->assertContains('bot_external_log.DEBUG: my 50% debug', $file_contents);
$this->assertContains('bot_external_log.DEBUG: my old custom placeholder debug', $file_contents);
$this->assertContains('bot_external_log.DEBUG: my new custom placeholder debug', $file_contents);
} }
} }
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment