Skip to content

Commit

Permalink
[4.0] Change how uncaught exceptions are processed (#20109)
Browse files Browse the repository at this point in the history
* Change how uncaught exceptions are processed

* Add event to be dispatched on errors, refactor redirect plugin

* Declare dependency
  • Loading branch information
Michael Babker authored and wilsonge committed May 15, 2018
1 parent 6ce4a24 commit 7775baf
Show file tree
Hide file tree
Showing 9 changed files with 191 additions and 132 deletions.
1 change: 1 addition & 0 deletions composer.json
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,7 @@
"phpmailer/phpmailer": "~6.0",
"psr/link": "~1.0",
"symfony/console": "3.4.*",
"symfony/debug": "3.4.*",
"symfony/web-link": "3.4.*",
"symfony/yaml": "3.4.*"
},
Expand Down
2 changes: 1 addition & 1 deletion composer.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

36 changes: 22 additions & 14 deletions installation/src/Application/InstallationApplication.php
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
use Joomla\CMS\Date\Date;
use Joomla\CMS\Document\HtmlDocument;
use Joomla\CMS\Document\FactoryInterface;
use Joomla\CMS\Exception\ExceptionHandler;
use Joomla\CMS\Factory;
use Joomla\CMS\Input\Input;
use Joomla\CMS\Language\LanguageHelper;
Expand Down Expand Up @@ -232,24 +233,31 @@ protected function doExecute()
*/
public function execute()
{
// Perform application routines.
$this->doExecute();

// If we have an application document object, render it.
if ($this->document instanceof Document)
try
{
// Render the application output.
$this->render();
}
// Perform application routines.
$this->doExecute();

// If we have an application document object, render it.
if ($this->document instanceof Document)
{
// Render the application output.
$this->render();
}

// If gzip compression is enabled in configuration and the server is compliant, compress the output.
if ($this->get('gzip') && !ini_get('zlib.output_compression') && (ini_get('output_handler') != 'ob_gzhandler'))
// If gzip compression is enabled in configuration and the server is compliant, compress the output.
if ($this->get('gzip') && !ini_get('zlib.output_compression') && (ini_get('output_handler') != 'ob_gzhandler'))
{
$this->compress();
}

// Send the application response.
$this->respond();
}
catch (\Throwable $throwable)
{
$this->compress();
ExceptionHandler::render($throwable);
}

// Send the application response.
$this->respond();
}

/**
Expand Down
2 changes: 1 addition & 1 deletion libraries/bootstrap.php
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,7 @@
require_once JPATH_LIBRARIES . '/classmap.php';

// Register the global exception handler.
set_exception_handler(['JErrorPage', 'render']);
\Symfony\Component\Debug\ExceptionHandler::register(false);

// Register the error handler which processes E_USER_DEPRECATED errors
set_error_handler(['JErrorPage', 'handleUserDeprecatedErrors'], E_USER_DEPRECATED);
Expand Down
75 changes: 47 additions & 28 deletions libraries/src/Application/CMSApplication.php
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,8 @@
use Joomla\CMS\Authentication\Authentication;
use Joomla\CMS\Event\AbstractEvent;
use Joomla\CMS\Event\BeforeExecuteEvent;
use Joomla\CMS\Event\ErrorEvent;
use Joomla\CMS\Exception\ExceptionHandler;
use Joomla\CMS\Extension\ExtensionManagerTrait;
use Joomla\CMS\Input\Input;
use Joomla\CMS\Language\Language;
Expand Down Expand Up @@ -347,50 +349,67 @@ public function enqueueMessage($msg, $type = self::MSG_INFO)
*/
public function execute()
{
$this->createExtensionNamespaceMap();
try
{
$this->createExtensionNamespaceMap();

PluginHelper::importPlugin('system');
PluginHelper::importPlugin('system');

// Trigger the onBeforeExecute event.
$this->triggerEvent(
'onBeforeExecute',
AbstractEvent::create(
// Trigger the onBeforeExecute event.
$this->triggerEvent(
'onBeforeExecute',
[
'subject' => $this,
'eventClass' => BeforeExecuteEvent::class,
'container' => $this->getContainer()
]
)
);
);

// Mark beforeExecute in the profiler.
JDEBUG ? $this->profiler->mark('beforeExecute event dispatched') : null;
// Mark beforeExecute in the profiler.
JDEBUG ? $this->profiler->mark('beforeExecute event dispatched') : null;

// Perform application routines.
$this->doExecute();
// Perform application routines.
$this->doExecute();

// If we have an application document object, render it.
if ($this->document instanceof \JDocument)
{
// Render the application output.
$this->render();
}
// If we have an application document object, render it.
if ($this->document instanceof \JDocument)
{
// Render the application output.
$this->render();
}

// If gzip compression is enabled in configuration and the server is compliant, compress the output.
if ($this->get('gzip') && !ini_get('zlib.output_compression') && ini_get('output_handler') !== 'ob_gzhandler')
{
$this->compress();
// If gzip compression is enabled in configuration and the server is compliant, compress the output.
if ($this->get('gzip') && !ini_get('zlib.output_compression') && ini_get('output_handler') !== 'ob_gzhandler')
{
$this->compress();

// Trigger the onAfterCompress event.
$this->triggerEvent('onAfterCompress');
}

// Trigger the onAfterCompress event.
$this->triggerEvent('onAfterCompress');
// Send the application response.
$this->respond();

// Trigger the onAfterRespond event.
$this->triggerEvent('onAfterRespond');
}
catch (\Throwable $throwable)
{
/** @var ErrorEvent $event */
$event = AbstractEvent::create(
'onError',
[
'subject' => $throwable,
'eventClass' => ErrorEvent::class,
'application' => $this,
]
);

// Send the application response.
$this->respond();
// Trigger the onError event.
$this->triggerEvent('onError', $event);

// Trigger the onAfterRespond event.
$this->triggerEvent('onAfterRespond');
ExceptionHandler::render($event->getError());
}
}

/**
Expand Down
59 changes: 59 additions & 0 deletions libraries/src/Event/ErrorEvent.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
<?php
/**
* Joomla! Content Management System
*
* @copyright Copyright (C) 2005 - 2017 Open Source Matters, Inc. All rights reserved.
* @license GNU General Public License version 2 or later; see LICENSE
*/

namespace Joomla\CMS\Event;

defined('JPATH_PLATFORM') or die;

use Joomla\Application\AbstractApplication;

/**
* Event class for representing the application's `onError` event
*
* @since __DEPLOY_VERSION__
*/
class ErrorEvent extends AbstractEvent
{
/**
* Get the event's application object
*
* @return AbstractApplication
*
* @since __DEPLOY_VERSION__
*/
public function getApplication(): AbstractApplication
{
return $this->getArgument('application');
}

/**
* Get the event's error object
*
* @return \Throwable
*
* @since __DEPLOY_VERSION__
*/
public function getError(): \Throwable
{
return $this->getArgument('subject');
}

/**
* Set the event's error object
*
* @param \Throwable $error The new error to process
*
* @return void
*
* @since __DEPLOY_VERSION__
*/
public function setError(\Throwable $error)
{
$this->setArgument('subject', $error);
}
}
3 changes: 1 addition & 2 deletions libraries/vendor/composer/autoload_classmap.php
Original file line number Diff line number Diff line change
Expand Up @@ -195,6 +195,7 @@
'Joomla\\CMS\\Event\\AfterExtensionBootEvent' => $baseDir . '/libraries/src/Event/AfterExtensionBootEvent.php',
'Joomla\\CMS\\Event\\BeforeExecuteEvent' => $baseDir . '/libraries/src/Event/BeforeExecuteEvent.php',
'Joomla\\CMS\\Event\\BeforeExtensionBootEvent' => $baseDir . '/libraries/src/Event/BeforeExtensionBootEvent.php',
'Joomla\\CMS\\Event\\ErrorEvent' => $baseDir . '/libraries/src/Event/ErrorEvent.php',
'Joomla\\CMS\\Event\\GenericEvent' => $baseDir . '/libraries/src/Event/GenericEvent.php',
'Joomla\\CMS\\Event\\Table\\AbstractEvent' => $baseDir . '/libraries/src/Event/Table/AbstractEvent.php',
'Joomla\\CMS\\Event\\Table\\AfterBindEvent' => $baseDir . '/libraries/src/Event/Table/AfterBindEvent.php',
Expand Down Expand Up @@ -781,8 +782,6 @@
'Psr\\Log\\LoggerInterface' => $vendorDir . '/psr/log/Psr/Log/LoggerInterface.php',
'Psr\\Log\\LoggerTrait' => $vendorDir . '/psr/log/Psr/Log/LoggerTrait.php',
'Psr\\Log\\NullLogger' => $vendorDir . '/psr/log/Psr/Log/NullLogger.php',
'Psr\\Log\\Test\\DummyTest' => $vendorDir . '/psr/log/Psr/Log/Test/LoggerInterfaceTest.php',
'Psr\\Log\\Test\\LoggerInterfaceTest' => $vendorDir . '/psr/log/Psr/Log/Test/LoggerInterfaceTest.php',
'ReCaptcha\\ReCaptcha' => $vendorDir . '/google/recaptcha/src/ReCaptcha/ReCaptcha.php',
'ReCaptcha\\RequestMethod' => $vendorDir . '/google/recaptcha/src/ReCaptcha/RequestMethod.php',
'ReCaptcha\\RequestMethod\\Curl' => $vendorDir . '/google/recaptcha/src/ReCaptcha/RequestMethod/Curl.php',
Expand Down
3 changes: 1 addition & 2 deletions libraries/vendor/composer/autoload_static.php
Original file line number Diff line number Diff line change
Expand Up @@ -455,6 +455,7 @@ class ComposerStaticInita4c4383b02fcf9dfb95cc0397c641cf1
'Joomla\\CMS\\Event\\AfterExtensionBootEvent' => __DIR__ . '/../../..' . '/libraries/src/Event/AfterExtensionBootEvent.php',
'Joomla\\CMS\\Event\\BeforeExecuteEvent' => __DIR__ . '/../../..' . '/libraries/src/Event/BeforeExecuteEvent.php',
'Joomla\\CMS\\Event\\BeforeExtensionBootEvent' => __DIR__ . '/../../..' . '/libraries/src/Event/BeforeExtensionBootEvent.php',
'Joomla\\CMS\\Event\\ErrorEvent' => __DIR__ . '/../../..' . '/libraries/src/Event/ErrorEvent.php',
'Joomla\\CMS\\Event\\GenericEvent' => __DIR__ . '/../../..' . '/libraries/src/Event/GenericEvent.php',
'Joomla\\CMS\\Event\\Table\\AbstractEvent' => __DIR__ . '/../../..' . '/libraries/src/Event/Table/AbstractEvent.php',
'Joomla\\CMS\\Event\\Table\\AfterBindEvent' => __DIR__ . '/../../..' . '/libraries/src/Event/Table/AfterBindEvent.php',
Expand Down Expand Up @@ -1041,8 +1042,6 @@ class ComposerStaticInita4c4383b02fcf9dfb95cc0397c641cf1
'Psr\\Log\\LoggerInterface' => __DIR__ . '/..' . '/psr/log/Psr/Log/LoggerInterface.php',
'Psr\\Log\\LoggerTrait' => __DIR__ . '/..' . '/psr/log/Psr/Log/LoggerTrait.php',
'Psr\\Log\\NullLogger' => __DIR__ . '/..' . '/psr/log/Psr/Log/NullLogger.php',
'Psr\\Log\\Test\\DummyTest' => __DIR__ . '/..' . '/psr/log/Psr/Log/Test/LoggerInterfaceTest.php',
'Psr\\Log\\Test\\LoggerInterfaceTest' => __DIR__ . '/..' . '/psr/log/Psr/Log/Test/LoggerInterfaceTest.php',
'ReCaptcha\\ReCaptcha' => __DIR__ . '/..' . '/google/recaptcha/src/ReCaptcha/ReCaptcha.php',
'ReCaptcha\\RequestMethod' => __DIR__ . '/..' . '/google/recaptcha/src/ReCaptcha/RequestMethod.php',
'ReCaptcha\\RequestMethod\\Curl' => __DIR__ . '/..' . '/google/recaptcha/src/ReCaptcha/RequestMethod/Curl.php',
Expand Down
Loading

0 comments on commit 7775baf

Please sign in to comment.