From 8d7602ef53fd3671e1bd6ad857950029672e8815 Mon Sep 17 00:00:00 2001 From: Johan Janssens Date: Mon, 29 Jun 2015 21:10:24 +0200 Subject: [PATCH 1/7] #163 - Add HTTP status codes and messages to allow for easy lookups. --- lib/libraries/joomla/http/response.php | 99 ++++++++++++++++++++++++++ 1 file changed, 99 insertions(+) diff --git a/lib/libraries/joomla/http/response.php b/lib/libraries/joomla/http/response.php index 793210bbef..4060f0132e 100644 --- a/lib/libraries/joomla/http/response.php +++ b/lib/libraries/joomla/http/response.php @@ -35,4 +35,103 @@ class JHttpResponse * @since 11.3 */ public $body; + + // [Successful 2xx] + const OK = 200; + const CREATED = 201; + const ACCEPTED = 202; + const NO_CONTENT = 204; + const RESET_CONTENT = 205; + const PARTIAL_CONTENT = 206; + + // [Redirection 3xx] + const MOVED_PERMANENTLY = 301; + const FOUND = 302; + const SEE_OTHER = 303; + const NOT_MODIFIED = 304; + const USE_PROXY = 305; + const TEMPORARY_REDIRECT = 307; + + // [Client Error 4xx] + const BAD_REQUEST = 400; + const UNAUTHORIZED = 401; + const FORBIDDEN = 403; + const NOT_FOUND = 404; + const METHOD_NOT_ALLOWED = 405; + const NOT_ACCEPTABLE = 406; + const REQUEST_TIMEOUT = 408; + const CONFLICT = 409; + const GONE = 410; + const LENGTH_REQUIRED = 411; + const PRECONDITION_FAILED = 412; + const REQUEST_ENTITY_TOO_LARGE = 413; + const REQUEST_URI_TOO_LONG = 414; + const UNSUPPORTED_MEDIA_TYPE = 415; + const REQUESTED_RANGE_NOT_SATISFIED = 416; + const EXPECTATION_FAILED = 417; + + // [Server Error 5xx] + const INTERNAL_SERVER_ERROR = 500; + const NOT_IMPLEMENTED = 501; + const BAD_GATEWAY = 502; + const SERVICE_UNAVAILABLE = 503; + const GATEWAY_TIMEOUT = 504; + const VERSION_NOT_SUPPORTED = 505; + + /** + * Status codes translation table. + * + * The list of codes is complete according to the + * {@link http://www.iana.org/assignments/http-status-codes/ Hypertext Transfer Protocol (HTTP) Status Code Registry} + * (last updated 2012-02-13). + * + * Unless otherwise noted, the status code is defined in RFC2616. + * + * @var array + */ + public static $status_messages = array( + + // [Successful 2xx] + 200 => 'OK', + 201 => 'Created', + 202 => 'Accepted', + 204 => 'No Content', + 205 => 'Reset Content', + 206 => 'Partial Content', + + // [Redirection 3xx] + 300 => 'Multiple Choices', + 301 => 'Moved Permanently', + 302 => 'Found', + 303 => 'See Other', + 304 => 'Not Modified', + 305 => 'Use Proxy', + 307 => 'Temporary Redirect', + + // [Client Error 4xx] + 400 => 'Bad Request', + 401 => 'Unauthorized', + 403 => 'Forbidden', + 404 => 'Not Found', + 405 => 'Method Not Allowed', + 406 => 'Not Acceptable', + 408 => 'Request Timeout', + 409 => 'Conflict', + 410 => 'Gone', + 411 => 'Length Required', + 412 => 'Precondition Failed', + 413 => 'Request Entity Too Large', + 414 => 'Request-URI Too Long', + 415 => 'Unsupported Media Type', + 416 => 'Requested Range Not Satisfiable', + 417 => 'Expectation Failed', + + // [Server Error 5xx] + 500 => 'Internal Server Error', + 501 => 'Not Implemented', + 502 => 'Bad Gateway', + 503 => 'Object Unavailable', + 504 => 'Gateway Timeout', + 505 => 'HTTP Version Not Supported' + ); } From a584b492ad30c1910eee30f08843f81db80fe4a2 Mon Sep 17 00:00:00 2001 From: Johan Janssens Date: Mon, 29 Jun 2015 21:13:39 +0200 Subject: [PATCH 2/7] #163 : Improve JPageError - Ensure the exception code is a valid HTTP status code, if not revert to '500'. - If display_errors is off, use the formal HTTP status message instead of the custom exception message to prevent system information leaking to the output. --- lib/libraries/cms/error/page.php | 45 +++++++++++++++++++------------- 1 file changed, 27 insertions(+), 18 deletions(-) diff --git a/lib/libraries/cms/error/page.php b/lib/libraries/cms/error/page.php index 5ce0ae567d..c7399c943d 100644 --- a/lib/libraries/cms/error/page.php +++ b/lib/libraries/cms/error/page.php @@ -34,10 +34,21 @@ public static function render(Exception $error) $app = JFactory::getApplication(); $document = JDocument::getInstance('error'); - if (!$document) + $code = $error->getCode(); + if(!isset(JHttpResponse::$status_messages[$code])) { + $code = '500'; + } + + if(ini_get('display_errors')) { + $message = $error->getMessage(); + } else { + $message = JHttpResponse::$status_messages[$code]; + } + + // Exit immediatly if we are in a CLI environment + if (PHP_SAPI == 'cli') { - // We're probably in an CLI environment - exit($error->getMessage()); + exit($message); $app->close(0); } @@ -46,15 +57,13 @@ public static function render(Exception $error) // Get the current template from the application $template = $app->getTemplate(); - // Push the error object into the document $document->setError($error); - if (ob_get_contents()) - { + if (ob_get_contents()) { ob_end_clean(); } - $document->setTitle(JText::_('Error') . ': ' . $error->getCode()); + $document->setTitle(JText::_('Error') . ': ' . $code); $data = $document->render( false, array('template' => $template, @@ -63,22 +72,22 @@ public static function render(Exception $error) ); // Failsafe to get the error displayed. - if (empty($data)) - { - exit($error->getMessage()); - } - else + if (!empty($data)) { - // Do not allow cache - $app->allowCache(false); + // Do not allow cache + $app->allowCache(false); - $app->setBody($data); - echo $app->toString(); + $app->setBody($data); + echo $app->toString(); } + else + { + exit($message); + } } catch (Exception $e) - { - exit('Error displaying the error page: ' . $e->getMessage() . ': ' . $error->getMessage()); + { + exit('Error displaying the error page: ' . $e->getMessage() . ': ' . $message); } } } From c1e3b27dee64d52417c93ad184bc8a2533a86245 Mon Sep 17 00:00:00 2001 From: Johan Janssens Date: Mon, 29 Jun 2015 21:15:51 +0200 Subject: [PATCH 3/7] #163 - Improve JDocumentError - Add 'code' parameter. Default to the exception code. - Add 'message' parameter. Default to the exception message. - Ensure the exception code is a valid HTTP status code, if not revert to '500'. - If display_errors is off, use the formal HTTP status message instead of the custom exception message to prevent system information leaking to the output. --- lib/libraries/joomla/document/error/error.php | 65 +++++++++++-------- 1 file changed, 38 insertions(+), 27 deletions(-) diff --git a/lib/libraries/joomla/document/error/error.php b/lib/libraries/joomla/document/error/error.php index 17416d156c..98fe00b7dc 100644 --- a/lib/libraries/joomla/document/error/error.php +++ b/lib/libraries/joomla/document/error/error.php @@ -79,35 +79,46 @@ public function setError($error) public function render($cache = false, $params = array()) { // If no error object is set return null - if (!isset($this->_error)) + if (isset($this->_error)) { - return; + $code = $$this->_error->getCode(); + if(!isset(JHttpResponse::$status_messages[$code])) { + $code = '500'; + } + + if(ini_get('display_errors')) { + $message = $this->_error->getMessage(); + } else { + $message = JHttpResponse::$status_messages[$code]; + } + + // Set the status header + JFactory::getApplication()->setHeader('status', $code . ' ' . str_replace("\n", ' ', $message)); + $file = 'error.php'; + + // Check template + $directory = isset($params['directory']) ? $params['directory'] : 'templates'; + $template = isset($params['template']) ? JFilterInput::getInstance()->clean($params['template'], 'cmd') : 'system'; + + if (!file_exists($directory . '/' . $template . '/' . $file)) + { + $template = 'system'; + } + + // Set variables + $this->baseurl = JUri::base(true); + $this->template = $template; + $this->error = $this->_error; + $this->debug = isset($params['debug']) ? $params['debug'] : false; + $this->code = isset($params['code']) ? $params['code'] : $code; + $this->message = isset($params['message']) ? $params['message'] : $message; + + // Load + $data = $this->_loadTemplate($directory . '/' . $template, $file); + + parent::render(); + return $data; } - - // Set the status header - JFactory::getApplication()->setHeader('status', $this->_error->getCode() . ' ' . str_replace("\n", ' ', $this->_error->getMessage())); - $file = 'error.php'; - - // Check template - $directory = isset($params['directory']) ? $params['directory'] : 'templates'; - $template = isset($params['template']) ? JFilterInput::getInstance()->clean($params['template'], 'cmd') : 'system'; - - if (!file_exists($directory . '/' . $template . '/' . $file)) - { - $template = 'system'; - } - - // Set variables - $this->baseurl = JUri::base(true); - $this->template = $template; - $this->debug = isset($params['debug']) ? $params['debug'] : false; - $this->error = $this->_error; - - // Load - $data = $this->_loadTemplate($directory . '/' . $template, $file); - - parent::render(); - return $data; } /** From 04615a45dcfc14cce65f703cf04242c9f8bb2559 Mon Sep 17 00:00:00 2001 From: Johan Janssens Date: Mon, 29 Jun 2015 21:16:19 +0200 Subject: [PATCH 4/7] #163 - Use 'code' and 'message' parameters. --- web/administrator/templates/isis/error.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/web/administrator/templates/isis/error.php b/web/administrator/templates/isis/error.php index 84aa5c5c79..ec75b6f621 100644 --- a/web/administrator/templates/isis/error.php +++ b/web/administrator/templates/isis/error.php @@ -63,7 +63,7 @@ - <?php echo $this->title; ?> <?php echo htmlspecialchars($this->error->getMessage(), ENT_QUOTES, 'UTF-8'); ?> + <?php echo $this->title; ?> <?php echo htmlspecialchars($this->message, ENT_QUOTES, 'UTF-8'); ?> get('debug_lang', '0') == '1' || $app->get('debug', '0') == '1') : ?> @@ -221,7 +221,7 @@

- error->getCode(); ?> error->getMessage(), ENT_QUOTES, 'UTF-8');?> + code; ?> message, ENT_QUOTES, 'UTF-8');?>

From 82e252dbb7e1af58447701c6a6cc8658ef14dbec Mon Sep 17 00:00:00 2001 From: Johan Janssens Date: Mon, 29 Jun 2015 21:16:55 +0200 Subject: [PATCH 5/7] #163 - Use 'code' and 'message' parameters. Only show the backtrace if display_errors is TRUE. --- web/administrator/templates/system/error.php | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/web/administrator/templates/system/error.php b/web/administrator/templates/system/error.php index 2777c59278..f491793618 100644 --- a/web/administrator/templates/system/error.php +++ b/web/administrator/templates/system/error.php @@ -13,24 +13,24 @@ - <?php echo $this->error->getCode(); ?> - <?php echo htmlspecialchars($this->error->getMessage(), ENT_QUOTES, 'UTF-8'); ?> + <?php echo $this->error->getCode(); ?> - <?php echo htmlspecialchars($this->message, ENT_QUOTES, 'UTF-8'); ?> - +

- error->getCode() ?> - + code ?> -

-

error->getMessage(), ENT_QUOTES, 'UTF-8'); ?>

+

message, ENT_QUOTES, 'UTF-8'); ?>

- debug) : + debug && ini_get('display_errors')) : echo $this->renderBacktrace(); endif; ?>

From e2fc8d4e0b407308c3a3127dcddb31f2ed0ae0a7 Mon Sep 17 00:00:00 2001 From: Johan Janssens Date: Tue, 14 Jul 2015 20:41:49 +0200 Subject: [PATCH 6/7] #163 - Fix typo --- lib/libraries/joomla/document/error/error.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/libraries/joomla/document/error/error.php b/lib/libraries/joomla/document/error/error.php index 98fe00b7dc..c6db8b88c1 100644 --- a/lib/libraries/joomla/document/error/error.php +++ b/lib/libraries/joomla/document/error/error.php @@ -81,7 +81,7 @@ public function render($cache = false, $params = array()) // If no error object is set return null if (isset($this->_error)) { - $code = $$this->_error->getCode(); + $code = $this->_error->getCode(); if(!isset(JHttpResponse::$status_messages[$code])) { $code = '500'; } From d2c24ab3bd0c17f41c4ede2a41ff0a2b4564949b Mon Sep 17 00:00:00 2001 From: Johan Janssens Date: Tue, 14 Jul 2015 20:42:21 +0200 Subject: [PATCH 7/7] #163 - Add additional !$document check. --- lib/libraries/cms/error/page.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/libraries/cms/error/page.php b/lib/libraries/cms/error/page.php index c7399c943d..0801ef4ca5 100644 --- a/lib/libraries/cms/error/page.php +++ b/lib/libraries/cms/error/page.php @@ -46,7 +46,7 @@ public static function render(Exception $error) } // Exit immediatly if we are in a CLI environment - if (PHP_SAPI == 'cli') + if (!$document || PHP_SAPI == 'cli') { exit($message); $app->close(0);