diff --git a/.travis.yml b/.travis.yml index 3b1d5df58..be56d8875 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,9 +1,5 @@ language: php php: - - 5.4 - - 5.5 - - 5.6 - - 7.0 - 7.1 - 7.2 @@ -31,7 +27,7 @@ jobs: php: 7.1 install: # Install Nette Code Checker - - travis_retry composer create-project nette/code-checker temp/code-checker ~2 --no-progress + - travis_retry composer create-project nette/code-checker temp/code-checker ^3.0 --no-progress # Install Nette Coding Standard - travis_retry composer create-project nette/coding-standard temp/coding-standard --no-progress # Install new Node.js and Eslint @@ -40,7 +36,7 @@ jobs: - nvm use stable - npm install eslint script: - - php temp/code-checker/src/code-checker.php --short-arrays -i tests/Tracy/fixtures -i examples/assets + - php temp/code-checker/src/code-checker.php --strict-types -i tests/Tracy/fixtures -i examples/assets - php temp/coding-standard/ecs check src tests examples tools --config tests/coding-standard.neon - ./node_modules/.bin/eslint "src/**/*.js" diff --git a/appveyor.yml b/appveyor.yml index f198beafb..f682febe0 100644 --- a/appveyor.yml +++ b/appveyor.yml @@ -14,7 +14,7 @@ install: # Install PHP - IF EXIST c:\php (SET PHP=0) ELSE (mkdir c:\php) - IF %PHP%==1 cd c:\php - - IF %PHP%==1 curl https://windows.php.net/downloads/releases/archives/php-5.6.14-Win32-VC11-x86.zip --output php.zip + - IF %PHP%==1 curl https://windows.php.net/downloads/releases/archives/php-7.1.17-Win32-VC14-x64.zip --output php.zip - IF %PHP%==1 7z x php.zip >nul - IF %PHP%==1 echo extension_dir=ext >> php.ini - IF %PHP%==1 echo extension=php_openssl.dll >> php.ini diff --git a/composer.json b/composer.json index f170f0ae3..2830ef33b 100644 --- a/composer.json +++ b/composer.json @@ -15,13 +15,14 @@ } ], "require": { - "php": ">=5.4.4", + "php": ">=7.1", "ext-session": "*", "ext-json": "*" }, "require-dev": { - "nette/di": "~2.3", - "nette/tester": "~1.7" + "nette/di": "^2.4 || ^3.0", + "nette/tester": "^2.0", + "psr/log": "^1.0" }, "suggest": { "https://nette.org/donate": "Please support Tracy via a donation" @@ -33,7 +34,7 @@ "minimum-stability": "dev", "extra": { "branch-alias": { - "dev-master": "2.5-dev" + "dev-master": "3.0-dev" } } } diff --git a/examples/ajax.php b/examples/ajax.php index 99b6b7e9d..2949c96a7 100644 --- a/examples/ajax.php +++ b/examples/ajax.php @@ -1,5 +1,7 @@ addPanel(function ($e) { + $blueScreen->addPanel(function ($e): ?array { if ($e instanceof Latte\CompileException) { return [ 'tab' => 'Template', @@ -39,9 +41,10 @@ public static function initialize() . '', ]; } + return null; }); - $blueScreen->addAction(function ($e) { + $blueScreen->addAction(function ($e): ?array { if ( $e instanceof Latte\CompileException && @is_file($e->sourceName) // @ - may trigger error @@ -53,9 +56,10 @@ public static function initialize() 'label' => 'fix it', ]; } + return null; }); - $blueScreen->addAction(function ($e) { + $blueScreen->addAction(function ($e): ?array { if ($e instanceof Nette\MemberAccessException || $e instanceof \LogicException) { $loc = $e instanceof Nette\MemberAccessException ? $e->getTrace()[1] : $e->getTrace()[0]; if (preg_match('#Cannot (?:read|write to) an undeclared property .+::\$(\w+), did you mean \$(\w+)\?#A', $e->getMessage(), $m)) { // @ - may trigger error @@ -71,9 +75,10 @@ public static function initialize() ]; } } + return null; }); - $blueScreen->addPanel(function ($e) { + $blueScreen->addPanel(function ($e): ?array { if ( $e instanceof Nette\Neon\Exception && preg_match('#line (\d+)#', $e->getMessage(), $m) @@ -87,6 +92,7 @@ public static function initialize() : BlueScreen::highlightPhp($trace['args'][0], $m[1]), ]; } + return null; }); } } diff --git a/src/Bridges/Nette/MailSender.php b/src/Bridges/Nette/MailSender.php index 4658d584e..f59f412e7 100644 --- a/src/Bridges/Nette/MailSender.php +++ b/src/Bridges/Nette/MailSender.php @@ -5,6 +5,8 @@ * Copyright (c) 2004 David Grudl (https://davidgrudl.com) */ +declare(strict_types=1); + namespace Tracy\Bridges\Nette; use Nette; @@ -25,7 +27,7 @@ class MailSender private $fromEmail; - public function __construct(Nette\Mail\IMailer $mailer, $fromEmail = null) + public function __construct(Nette\Mail\IMailer $mailer, string $fromEmail = null) { $this->mailer = $mailer; $this->fromEmail = $fromEmail; @@ -34,12 +36,10 @@ public function __construct(Nette\Mail\IMailer $mailer, $fromEmail = null) /** * @param mixed $message - * @param string $email - * @return void */ - public function send($message, $email) + public function send($message, string $email): void { - $host = preg_replace('#[^\w.-]+#', '', isset($_SERVER['HTTP_HOST']) ? $_SERVER['HTTP_HOST'] : php_uname('n')); + $host = preg_replace('#[^\w.-]+#', '', $_SERVER['HTTP_HOST'] ?? php_uname('n')); $mail = new Nette\Mail\Message; $mail->setHeader('X-Mailer', 'Tracy'); diff --git a/src/Bridges/Nette/TracyExtension.php b/src/Bridges/Nette/TracyExtension.php index 2398c3927..aafe4620b 100644 --- a/src/Bridges/Nette/TracyExtension.php +++ b/src/Bridges/Nette/TracyExtension.php @@ -5,6 +5,8 @@ * Copyright (c) 2004 David Grudl (https://davidgrudl.com) */ +declare(strict_types=1); + namespace Tracy\Bridges\Nette; use Nette; @@ -43,7 +45,7 @@ class TracyExtension extends Nette\DI\CompilerExtension private $cliMode; - public function __construct($debugMode = false, $cliMode = false) + public function __construct(bool $debugMode = false, bool $cliMode = false) { $this->debugMode = $debugMode; $this->cliMode = $cliMode; @@ -93,13 +95,13 @@ public function afterCompile(Nette\PhpGenerator\ClassType $class) } $logger = $builder->getDefinition($this->prefix('logger')); - if ($logger->getFactory()->getEntity() !== ['Tracy\Debugger', 'getLogger']) { + if ($logger->getFactory()->getEntity() !== [Tracy\Debugger::class, 'getLogger']) { $initialize->addBody($builder->formatPhp('Tracy\Debugger::setLogger(?);', [$logger])); } - if ($this->config['netteMailer'] && $builder->getByType('Nette\Mail\IMailer')) { + if ($this->config['netteMailer'] && $builder->getByType(Nette\Mail\IMailer::class)) { $initialize->addBody($builder->formatPhp('Tracy\Debugger::getLogger(?)->mailer = ?;', [ $logger, - [new Nette\DI\Statement('Tracy\Bridges\Nette\MailSender', ['fromEmail' => $this->config['fromEmail']]), 'send'], + [new Nette\DI\Statement(Tracy\Bridges\Nette\MailSender::class, ['fromEmail' => $this->config['fromEmail']]), 'send'], ])); } diff --git a/src/Bridges/Psr/PsrToTracyLoggerAdapter.php b/src/Bridges/Psr/PsrToTracyLoggerAdapter.php new file mode 100644 index 000000000..9f20389b1 --- /dev/null +++ b/src/Bridges/Psr/PsrToTracyLoggerAdapter.php @@ -0,0 +1,62 @@ + Psr\Log\LogLevel::DEBUG, + Tracy\ILogger::INFO => Psr\Log\LogLevel::INFO, + Tracy\ILogger::WARNING => Psr\Log\LogLevel::WARNING, + Tracy\ILogger::ERROR => Psr\Log\LogLevel::ERROR, + Tracy\ILogger::EXCEPTION => Psr\Log\LogLevel::ERROR, + Tracy\ILogger::CRITICAL => Psr\Log\LogLevel::CRITICAL, + ]; + + /** @var Psr\Log\LoggerInterface */ + private $psrLogger; + + + public function __construct(Psr\Log\LoggerInterface $psrLogger) + { + $this->psrLogger = $psrLogger; + } + + + public function log($value, string $priority = self::INFO) + { + if ($value instanceof \Throwable) { + $message = $value->getMessage(); + $context = ['exception' => $value]; + + } elseif (!is_string($value)) { + $message = trim(Tracy\Dumper::toText($value)); + $context = []; + + } else { + $message = $value; + $context = []; + } + + $this->psrLogger->log( + self::PRIORITY_MAP[$priority] ?? Psr\Log\LogLevel::ERROR, + $message, + $context + ); + } +} diff --git a/src/Bridges/Psr/TracyToPsrLoggerAdapter.php b/src/Bridges/Psr/TracyToPsrLoggerAdapter.php new file mode 100644 index 000000000..155290bf8 --- /dev/null +++ b/src/Bridges/Psr/TracyToPsrLoggerAdapter.php @@ -0,0 +1,61 @@ + Tracy\ILogger::CRITICAL, + Psr\Log\LogLevel::ALERT => Tracy\ILogger::CRITICAL, + Psr\Log\LogLevel::CRITICAL => Tracy\ILogger::CRITICAL, + Psr\Log\LogLevel::ERROR => Tracy\ILogger::ERROR, + Psr\Log\LogLevel::WARNING => Tracy\ILogger::WARNING, + Psr\Log\LogLevel::NOTICE => Tracy\ILogger::WARNING, + Psr\Log\LogLevel::INFO => Tracy\ILogger::INFO, + Psr\Log\LogLevel::DEBUG => Tracy\ILogger::DEBUG, + ]; + + /** @var Tracy\ILogger */ + private $tracyLogger; + + + public function __construct(Tracy\ILogger $tracyLogger) + { + $this->tracyLogger = $tracyLogger; + } + + + public function log($level, $message, array $context = []) + { + $priority = self::PRIORITY_MAP[$level] ?? Tracy\ILogger::ERROR; + + if (isset($context['exception']) && $context['exception'] instanceof \Throwable) { + $this->tracyLogger->log($context['exception'], $priority); + unset($context['exception']); + } + + if ($context) { + $message = [ + 'message' => $message, + 'context' => $context, + ]; + } + + $this->tracyLogger->log($message, $priority); + } +} diff --git a/src/Tracy/Bar.php b/src/Tracy/Bar.php index 746cb5bd3..247163613 100644 --- a/src/Tracy/Bar.php +++ b/src/Tracy/Bar.php @@ -5,6 +5,8 @@ * Copyright (c) 2004 David Grudl (https://davidgrudl.com) */ +declare(strict_types=1); + namespace Tracy; @@ -25,11 +27,9 @@ class Bar /** * Add custom panel. - * @param IBarPanel $panel - * @param string $id * @return static */ - public function addPanel(IBarPanel $panel, $id = null) + public function addPanel(IBarPanel $panel, string $id = null): self { if ($id === null) { $c = 0; @@ -44,20 +44,17 @@ public function addPanel(IBarPanel $panel, $id = null) /** * Returns panel with given id - * @param string $id - * @return IBarPanel|null */ - public function getPanel($id) + public function getPanel(string $id): ?IBarPanel { - return isset($this->panels[$id]) ? $this->panels[$id] : null; + return $this->panels[$id] ?? null; } /** * Renders loading - -
- - - - -Fatal Error
- -File: %a%
-%d%: -%d%: -%d%: function second($arg1, $arg2) -%d%: { -%d%: third([1, 2, 3]); -%d%: } -%d%: -%d%: -%d%: function third($arg1) -%d%: { -%d%: missing_function(); -%d%: } -%d%: -%d%: -%d%: first(10, 'any string'); -
empty
-empty
-empty
-%A%-
Fatal Error
- -File: %a%
-%d%: -%d%: -%d%: function second($arg1, $arg2) -%d%: { -%d%: third([1, 2, 3]); -%d%: } -%d%: -%d%: -%d%: function third($arg1) -%d%: { -%d%: missing_function(); -%d%: } -%d%: -%d%: -%d%: first(10, 'any string'); -
- - %a% - source - third() -
- -%d%: -%d%: -%d%: function first($arg1, $arg2) -%d%: { -%d%: second(true, false); -%d%: } -%d%: -%d%: -%d%: function second($arg1, $arg2) -%d%: { -%d%: third([1, 2, 3]); -%d%: } -%d%: -%d%: -%d%: function third($arg1) -
- - %a% - source - second() -
- -- - - -%d%:%A%
- - %a% - source - first() -
- -%d%: third([1, 2, 3]); -%d%: } -%d%: -%d%: -%d%: function third($arg1) -%d%: { -%d%: missing_function(); -%d%: } -%d%: -%d%: -%d%: first(10, 'any string'); -%d%: -
empty
-empty
-empty
-%A%-