- deprecate functions Smarty::muteExpectedErrors() and Smarty::unmuteExpectedErrors()

as Smarty does no longer use error suppression like @filemtime().
    for backward compatibility code is moved from Smarty class to an external class and still can be
    called.
This commit is contained in:
Uwe Tews
2017-10-26 06:00:40 +02:00
parent 926ed8714b
commit 4575a31e62
5 changed files with 153 additions and 146 deletions

View File

@@ -4,6 +4,12 @@ This file contains a brief description of new features which have been added to
Smarty 3.1.32
Deprecate functions Smarty::muteExpectedErrors() and Smarty::unmuteExpectedErrors()
===================================================================================
These functions to start a special error handler are no longer needed as Smarty does
no longer use error suppression like @filemtime().
For backward compatibility the functions still can be called.
Using literals containing Smarty's left and right delimiter
===========================================================
New Methods

View File

@@ -2,6 +2,10 @@
26.10.2017 3.1.32-dev-28
- bugfix Smarty version was not filled in header comment of compiled and cached files
- optimization replace internal Smarty::$ds property by DIRECTORY_SEPARATOR
- deprecate functions Smarty::muteExpectedErrors() and Smarty::unmuteExpectedErrors()
as Smarty does no longer use error suppression like @filemtime().
for backward compatibility code is moved from Smarty class to an external class and still can be
called.
21.10.2017
- bugfix custom delimiters could fail since modification of version 3.1.32-dev-23

View File

@@ -100,7 +100,7 @@ class Smarty extends Smarty_Internal_TemplateBase
/**
* smarty version
*/
const SMARTY_VERSION = '3.1.32-dev-28';
const SMARTY_VERSION = '3.1.32-dev-29';
/**
* define variable scopes
*/
@@ -166,14 +166,6 @@ class Smarty extends Smarty_Internal_TemplateBase
* assigned global tpl vars
*/
public static $global_tpl_vars = array();
/**
* error handler returned by set_error_handler() in Smarty::muteExpectedErrors()
*/
public static $_previous_error_handler = null;
/**
* contains directories outside of SMARTY_DIR that are to be muted by muteExpectedErrors()
*/
public static $_muted_directories = array();
/**
* Flag denoting if Multibyte String functions are available
*/
@@ -625,99 +617,21 @@ class Smarty extends Smarty_Internal_TemplateBase
}
}
/**
* Error Handler to mute expected messages
*
* @link http://php.net/set_error_handler
*
* @param integer $errno Error level
* @param $errstr
* @param $errfile
* @param $errline
* @param $errcontext
*
* @return bool|void
*/
public static function mutingErrorHandler($errno, $errstr, $errfile, $errline, $errcontext)
{
$_is_muted_directory = false;
// add the SMARTY_DIR to the list of muted directories
if (!isset(Smarty::$_muted_directories[ SMARTY_DIR ])) {
$smarty_dir = realpath(SMARTY_DIR);
if ($smarty_dir !== false) {
Smarty::$_muted_directories[ SMARTY_DIR ] =
array('file' => $smarty_dir, 'length' => strlen($smarty_dir),);
}
}
// walk the muted directories and test against $errfile
foreach (Smarty::$_muted_directories as $key => &$dir) {
if (!$dir) {
// resolve directory and length for speedy comparisons
$file = realpath($key);
if ($file === false) {
// this directory does not exist, remove and skip it
unset(Smarty::$_muted_directories[ $key ]);
continue;
}
$dir = array('file' => $file, 'length' => strlen($file),);
}
if (!strncmp($errfile, $dir[ 'file' ], $dir[ 'length' ])) {
$_is_muted_directory = true;
break;
}
}
// pass to next error handler if this error did not occur inside SMARTY_DIR
// or the error was within smarty but masked to be ignored
if (!$_is_muted_directory || ($errno && $errno & error_reporting())) {
if (Smarty::$_previous_error_handler) {
return call_user_func(Smarty::$_previous_error_handler,
$errno,
$errstr,
$errfile,
$errline,
$errcontext);
} else {
return false;
}
}
return;
}
/**
* Enable error handler to mute expected messages
*
* @return void
* @deprecated
*/
public static function muteExpectedErrors()
{
/*
error muting is done because some people implemented custom error_handlers using
http://php.net/set_error_handler and for some reason did not understand the following paragraph:
It is important to remember that the standard PHP error handler is completely bypassed for the
error types specified by error_types unless the callback function returns FALSE.
error_reporting() settings will have no effect and your error handler will be called regardless -
however you are still able to read the current value of error_reporting and act appropriately.
Of particular note is that this value will be 0 if the statement that caused the error was
prepended by the @ error-control operator.
Smarty deliberately uses @filemtime() over file_exists() and filemtime() in some places. Reasons include
- @filemtime() is almost twice as fast as using an additional file_exists()
- between file_exists() and filemtime() a possible race condition is opened,
which does not exist using the simple @filemtime() approach.
*/
$error_handler = array('Smarty', 'mutingErrorHandler');
$previous = set_error_handler($error_handler);
// avoid dead loops
if ($previous !== $error_handler) {
Smarty::$_previous_error_handler = $previous;
}
return Smarty_Internal_ErrorHandler::muteExpectedErrors();
}
/**
* Disable error handler muting expected messages
*
* @return void
* @deprecated
*/
public static function unmuteExpectedErrors()
{

View File

@@ -0,0 +1,112 @@
<?php
/**
* Smarty error handler
*
*
* @package Smarty
* @subpackage PluginsInternal
* @author Uwe Tews
*
* @deprecated
Smarty does no longer use @filemtime()
*/
class Smarty_Internal_ErrorHandler
{
/**
* contains directories outside of SMARTY_DIR that are to be muted by muteExpectedErrors()
*/
public static $mutedDirectories = array();
/**
* error handler returned by set_error_handler() in self::muteExpectedErrors()
*/
private static $previousErrorHandler = null;
/**
* Enable error handler to mute expected messages
*
* @return void
*/
public static function muteExpectedErrors()
{
/*
error muting is done because some people implemented custom error_handlers using
http://php.net/set_error_handler and for some reason did not understand the following paragraph:
It is important to remember that the standard PHP error handler is completely bypassed for the
error types specified by error_types unless the callback function returns FALSE.
error_reporting() settings will have no effect and your error handler will be called regardless -
however you are still able to read the current value of error_reporting and act appropriately.
Of particular note is that this value will be 0 if the statement that caused the error was
prepended by the @ error-control operator.
Smarty deliberately uses @filemtime() over file_exists() and filemtime() in some places. Reasons include
- @filemtime() is almost twice as fast as using an additional file_exists()
- between file_exists() and filemtime() a possible race condition is opened,
which does not exist using the simple @filemtime() approach.
*/
$error_handler = array('Smarty_Internal_ErrorHandler', 'mutingErrorHandler');
$previous = set_error_handler($error_handler);
// avoid dead loops
if ($previous !== $error_handler) {
self::$previousErrorHandler = $previous;
}
}
/**
* Error Handler to mute expected messages
*
* @link http://php.net/set_error_handler
*
* @param integer $errno Error level
* @param $errstr
* @param $errfile
* @param $errline
* @param $errcontext
*
* @return bool
*/
public static function mutingErrorHandler($errno, $errstr, $errfile, $errline, $errcontext)
{
$_is_muted_directory = false;
// add the SMARTY_DIR to the list of muted directories
if (!isset(self::$mutedDirectories[ SMARTY_DIR ])) {
$smarty_dir = realpath(SMARTY_DIR);
if ($smarty_dir !== false) {
self::$mutedDirectories[ SMARTY_DIR ] =
array('file' => $smarty_dir, 'length' => strlen($smarty_dir),);
}
}
// walk the muted directories and test against $errfile
foreach (self::$mutedDirectories as $key => &$dir) {
if (!$dir) {
// resolve directory and length for speedy comparisons
$file = realpath($key);
if ($file === false) {
// this directory does not exist, remove and skip it
unset(self::$mutedDirectories[ $key ]);
continue;
}
$dir = array('file' => $file, 'length' => strlen($file),);
}
if (!strncmp($errfile, $dir[ 'file' ], $dir[ 'length' ])) {
$_is_muted_directory = true;
break;
}
}
// pass to next error handler if this error did not occur inside SMARTY_DIR
// or the error was within smarty but masked to be ignored
if (!$_is_muted_directory || ($errno && $errno & error_reporting())) {
if (self::$previousErrorHandler) {
return call_user_func(self::$previousErrorHandler,
$errno,
$errstr,
$errfile,
$errline,
$errcontext);
} else {
return false;
}
}
}
}

View File

@@ -28,15 +28,12 @@ class Smarty_Internal_TestInstall
public static function testInstall(Smarty $smarty, &$errors = null)
{
$status = true;
if ($errors === null) {
echo "<PRE>\n";
echo "Smarty Installation test...\n";
echo "Testing template directory...\n";
}
$_stream_resolve_include_path = function_exists('stream_resolve_include_path');
// test if all registered template_dir are accessible
foreach ($smarty->getTemplateDir() as $template_dir) {
$_template_dir = $template_dir;
@@ -50,12 +47,10 @@ class Smarty_Internal_TestInstall
} else {
$template_dir = $smarty->ext->_getIncludePath->getIncludePath($_template_dir, null, $smarty);
}
if ($template_dir !== false) {
if ($errors === null) {
echo "$template_dir is OK.\n";
}
continue;
} else {
$status = false;
@@ -64,9 +59,8 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['template_dir'] = $message;
$errors[ 'template_dir' ] = $message;
}
continue;
}
} else {
@@ -75,20 +69,18 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['template_dir'] = $message;
$errors[ 'template_dir' ] = $message;
}
continue;
}
}
if (!is_dir($template_dir)) {
$status = false;
$message = "FAILED: $template_dir is not a directory";
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['template_dir'] = $message;
$errors[ 'template_dir' ] = $message;
}
} else if (!is_readable($template_dir)) {
$status = false;
@@ -96,7 +88,7 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['template_dir'] = $message;
$errors[ 'template_dir' ] = $message;
}
} else {
if ($errors === null) {
@@ -104,11 +96,9 @@ class Smarty_Internal_TestInstall
}
}
}
if ($errors === null) {
echo "Testing compile directory...\n";
}
// test if registered compile_dir is accessible
$__compile_dir = $smarty->getCompileDir();
$_compile_dir = realpath($__compile_dir);
@@ -118,7 +108,7 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['compile_dir'] = $message;
$errors[ 'compile_dir' ] = $message;
}
} else if (!is_dir($_compile_dir)) {
$status = false;
@@ -126,7 +116,7 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['compile_dir'] = $message;
$errors[ 'compile_dir' ] = $message;
}
} else if (!is_readable($_compile_dir)) {
$status = false;
@@ -134,7 +124,7 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['compile_dir'] = $message;
$errors[ 'compile_dir' ] = $message;
}
} else if (!is_writable($_compile_dir)) {
$status = false;
@@ -142,18 +132,16 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['compile_dir'] = $message;
$errors[ 'compile_dir' ] = $message;
}
} else {
if ($errors === null) {
echo "{$_compile_dir} is OK.\n";
}
}
if ($errors === null) {
echo "Testing plugins directory...\n";
}
// test if all registered plugins_dir are accessible
// and if core plugins directory is still registered
$_core_plugins_dir = realpath(dirname(__FILE__) . '/../plugins');
@@ -170,12 +158,10 @@ class Smarty_Internal_TestInstall
} else {
$plugin_dir = $smarty->ext->_getIncludePath->getIncludePath($_plugin_dir, null, $smarty);
}
if ($plugin_dir !== false) {
if ($errors === null) {
echo "$plugin_dir is OK.\n";
}
continue;
} else {
$status = false;
@@ -183,9 +169,8 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['plugins_dir'] = $message;
$errors[ 'plugins_dir' ] = $message;
}
continue;
}
} else {
@@ -194,20 +179,18 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['plugins_dir'] = $message;
$errors[ 'plugins_dir' ] = $message;
}
continue;
}
}
if (!is_dir($plugin_dir)) {
$status = false;
$message = "FAILED: $plugin_dir is not a directory";
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['plugins_dir'] = $message;
$errors[ 'plugins_dir' ] = $message;
}
} else if (!is_readable($plugin_dir)) {
$status = false;
@@ -215,7 +198,7 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['plugins_dir'] = $message;
$errors[ 'plugins_dir' ] = $message;
}
} else if ($_core_plugins_dir && $_core_plugins_dir == realpath($plugin_dir)) {
$_core_plugins_available = true;
@@ -233,15 +216,13 @@ class Smarty_Internal_TestInstall
$message = "WARNING: Smarty's own libs/plugins is not available";
if ($errors === null) {
echo $message . ".\n";
} else if (!isset($errors['plugins_dir'])) {
$errors['plugins_dir'] = $message;
} else if (!isset($errors[ 'plugins_dir' ])) {
$errors[ 'plugins_dir' ] = $message;
}
}
if ($errors === null) {
echo "Testing cache directory...\n";
}
// test if all registered cache_dir is accessible
$__cache_dir = $smarty->getCacheDir();
$_cache_dir = realpath($__cache_dir);
@@ -251,7 +232,7 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['cache_dir'] = $message;
$errors[ 'cache_dir' ] = $message;
}
} else if (!is_dir($_cache_dir)) {
$status = false;
@@ -259,7 +240,7 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['cache_dir'] = $message;
$errors[ 'cache_dir' ] = $message;
}
} else if (!is_readable($_cache_dir)) {
$status = false;
@@ -267,7 +248,7 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['cache_dir'] = $message;
$errors[ 'cache_dir' ] = $message;
}
} else if (!is_writable($_cache_dir)) {
$status = false;
@@ -275,18 +256,16 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['cache_dir'] = $message;
$errors[ 'cache_dir' ] = $message;
}
} else {
if ($errors === null) {
echo "{$_cache_dir} is OK.\n";
}
}
if ($errors === null) {
echo "Testing configs directory...\n";
}
// test if all registered config_dir are accessible
foreach ($smarty->getConfigDir() as $config_dir) {
$_config_dir = $config_dir;
@@ -299,12 +278,10 @@ class Smarty_Internal_TestInstall
} else {
$config_dir = $smarty->ext->_getIncludePath->getIncludePath($_config_dir, null, $smarty);
}
if ($config_dir !== false) {
if ($errors === null) {
echo "$config_dir is OK.\n";
}
continue;
} else {
$status = false;
@@ -312,9 +289,8 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['config_dir'] = $message;
$errors[ 'config_dir' ] = $message;
}
continue;
}
} else {
@@ -323,20 +299,18 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['config_dir'] = $message;
$errors[ 'config_dir' ] = $message;
}
continue;
}
}
if (!is_dir($config_dir)) {
$status = false;
$message = "FAILED: $config_dir is not a directory";
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['config_dir'] = $message;
$errors[ 'config_dir' ] = $message;
}
} else if (!is_readable($config_dir)) {
$status = false;
@@ -344,7 +318,7 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['config_dir'] = $message;
$errors[ 'config_dir' ] = $message;
}
} else {
if ($errors === null) {
@@ -352,7 +326,6 @@ class Smarty_Internal_TestInstall
}
}
}
if ($errors === null) {
echo "Testing sysplugin files...\n";
}
@@ -411,6 +384,7 @@ class Smarty_Internal_TestInstall
'smarty_internal_config_file_compiler.php' => true,
'smarty_internal_data.php' => true,
'smarty_internal_debug.php' => true,
'smarty_internal_errorhandler.php' => true,
'smarty_internal_extension_handler.php' => true,
'smarty_internal_method_addautoloadfilters.php' => true,
'smarty_internal_method_adddefaultmodifiers.php' => true,
@@ -524,7 +498,7 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['sysplugins'] = $message;
$errors[ 'sysplugins' ] = $message;
}
} else if ($errors === null) {
echo "... OK\n";
@@ -535,10 +509,9 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['sysplugins_dir_constant'] = $message;
$errors[ 'sysplugins_dir_constant' ] = $message;
}
}
if ($errors === null) {
echo "Testing plugin files...\n";
}
@@ -609,7 +582,7 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['plugins'] = $message;
$errors[ 'plugins' ] = $message;
}
} else if ($errors === null) {
echo "... OK\n";
@@ -620,15 +593,13 @@ class Smarty_Internal_TestInstall
if ($errors === null) {
echo $message . ".\n";
} else {
$errors['plugins_dir_constant'] = $message;
$errors[ 'plugins_dir_constant' ] = $message;
}
}
if ($errors === null) {
echo "Tests complete.\n";
echo "</PRE>\n";
}
return $status;
}
}