Рассмотрим этот простой дочерний класс PrettyPageHandler
class NewErrorHandler extends \Whoops\Handler\PrettyPageHandler
{
public $foo = null;
public function __construct()
{
parent::__construct();
}
public function handle()
{
$this->foo = 'bar';
echo 'executed';
}
}
Когда это используется так:
$errorHandler = new NewErrorHandler();
$whoops->pushHandler($errorHandler);
$whoops->register();
var_dump($errorHandler->foo);
$errorHandler->foo
пусто, но «выполнено» было напечатано. Похоже на то $this->foo = 'bar';
не был выполнен или аннулирован в процессе, хотя он должен был. Есть идеи почему?
Обновление 1
Я пытаюсь получить вывод handle();
через выходную буферизацию, которая работает нормально. Но в то же время я хочу установить переменную:
public function handle()
{
parent::handle();
$output = ob_get_clean();
echo 'executed';
$this->foo = 'bar';
}
$this->foo = 'bar';
кажется, не выполняется в этот момент, но «выполнено» печатается.
Обновление 2
Я пытаюсь определить, не зафиксирована ли ошибка, если это правда, делать такие вещи, как отправлять уведомления (например, по электронной почте / смс / и т. Д.). Если ошибка уже зарегистрирована, это означает, что она дублируется, больше не отправляйте уведомления. Вот немного больше кода, но упрощенного для ясности:
<?php
class NewErrorHandler extends \Whoops\Handler\PrettyPageHandler
{
private $errorHash;
private $isNewError;
public function __construct()
{
parent::__construct();
}
public function handle()
{
parent::handle();
$output = ob_get_clean();
$this->setErrorHash();
if (!$this->isDuplicateError()) {
$this->isNewError = true;
$this->log($output);
}
}
private function log(string $data): void
{
$filename = $this->errorHash . '.html';
file_put_contents('logs/errors/'. $filename, $data);
}
public function isDuplicateError(): bool
{
// code check if the file $this->errorHash.'.html' exists in logs/errors/
// ...
}
private function setErrorHash(): string
{
$ex = $this->getException();
$this->errorHash = md5($ex->getMessage() . $ex->getFile() . $ex->getLine() . $ex->getTraceAsString());
}
}
$errorHandler = new NewErrorHandler();
$whoops->pushHandler($errorHandler);
$whoops->register();
if ($errorHandler->isNewError == true)
{
// do something like send notifications... outside the child class.
}
Вопрос $errorHandler->isNewError
является нулевым, даже если это должно быть true
Обновление 3:
Я постараюсь объяснить, почему я должен работать. Вот основной пример того, что я пытаюсь сделать. Давайте представим, что есть упрощенный Whoops
класс называется FakeWhoops
<?php
class FakeWhoops
{
private $handler;
public function pushHandler(CustomHandler $handler)
{
$this->handler = $handler;
}
public function triggerError()
{
$this->handler->handle();
}
}
И это мой пользовательский обработчик:
class CustomHandler
{
public $foo;
public function handle()
{
$this->foo = true;
echo 'executed';
}
}
Теперь давайте запустим его и вызовем ложную ошибку:
$cH = new CustomHandler;
$fW = new FakeWhoops;
$fW->pushHandler($cH);
// let's trigger a fake error which should call CustomHandler::handle();
$fW->triggerError();
var_dump($cH->foo); // returns true, foo was set!
Как вы можете видеть здесь, это именно то, что я пытаюсь сделать, хотя с использованием реального Whoops
, Это та же самая простая идея. Но почему это работает на этом упрощенном примере, а не с Whoops
?
Задача ещё не решена.
Других решений пока нет …