Smarty 中可用的变量一般有三种:1、来自PHP页面,通过assign()方法传递的变量;2、保留变量,即相当于PHP中预定义的变量;3、从配置文件中读取的变量。引用方法很简单,我就不详细说明了,具体可见:这里。不过,我遇到一个问题,就是在模板中引用保留变量时,其值为空(null )。开始感觉比较奇怪,后发现是其引用于PHP的php.ini中register_long_arrays设置、Smarty对象的 request_use_auto_globals 属性有关。
一、保量变量值为空(null )
例如,在模板中使用下面的方式获取一个保留变量:
{$smarty.server.PHP_SELF} |
我原来的想法是,它应该返回一个相当于下面PHP的变量:
_SERVER["PHP_SELF"] |
但是,在测试环境中,发现其值为空(null),与预期不相符。
后查看编译后的页面:
引用
Smarty/templates_c/%%193/%%1934206966/test.php |
上面的语句被转换成如下的语句:
<?php echo $GLOBALS['HTTP_SERVER_VARS']['PHP_SELF']; ?> |
二、处理方法
从上面可知,Smarty 的保留变量会转换为$GLOBALS[‘HTTP_SERVER_VARS’]数组的元素。而该数组是否生效,与PHP配置文件/etc/php.ini 的设定有关:
引用
register_long_arrays = On |
只有当 register_long_arrays为打开状态时,$HTTP_*_VARS 变量才有效。而测试环境中,该值为Off,所以,当Smarty的保留变量为空值(null )。可见,这会对GET、POST、SERVER等保留变量都有影响。
三、注意事项
1、建议关闭 register_long_arrays
PHP手册中,有如下一段话:
引用
register_long_arrays boolean Tells PHP whether or not to register the deprecated long $HTTP_*_VARS type predefined variables. When On (default), long predefined PHP variables like $HTTP_GET_VARS will be defined. If you're not using them, it's recommended to turn them off, for performance reasons. Instead, use the superglobal arrays, like $_GET. This directive became available in PHP 5.0.0. Warning This feature has been DEPRECATED as of PHP 5.3.0. Relying on this feature is highly discouraged. |
也就是说,建议关闭该设定值,并且在PHP 5.3.0后该设定将会被取消。
2、更好的方法
实际上,Smarty也考虑到了该问题,并且提供了解决办法。就是在创建Smarty对象时,把其request_use_auto_globals值设置为true:
$smarty->request_use_auto_globals = true; |
Smarty手册的说明如下:
引用
指定Smarty是否使用php 的$HTTP_*_VARS[]数组变量(默认$request_use_auto_globals=false)或$_*[]数组 ($request_use_auto_globals=true)变量。这对使用了{$smarty.request.*},, {$smarty.get.*}等标记的模板有影响。值得注意的是:如果设置$request_use_auto_globals为真,variable.request.vars.order就无效了但php的gpc_order配置值还有作用。
可见,该值默认为false,即使用$HTTP_*_VARS[]数组变量。修改为true后,上面的保留变量会转换为:
<?php echo $_SERVER['PHP_SELF']; ?> |
这时,即可把 PHP设置中的register_long_arrays 关闭。
※ 注意:修改request_use_auto_globals 后,建议把templates_c/目录下的文件都清空,待Smarty重建。