关于smarty中的$cache_id及$compile_id
首先引用Smarty官方网站上的一段代码:
You can also pass a $cache_id as an optional second parameter in case you want multiple caches for the given template.
|
Above, we are passing the variable $my_cache_id to display() as the $cache_id. For each unique value of $my_cache_id, a separate cache will be generated for index.tpl. In this example, article_id was passed in the URL and is used as the $cache_id.
简单来说$cache_id就是用于通过一个模板文件,如上面的index.tpl来生成多个缓存文件,如index_1.html,index_2.html,1与2可以理解为url中的参数,这样通过一个url就能生成多个缓存页面,比如新闻系统里面可能就会用到这些
$compile_id
Smarty.class.php中的说明/**
* Set this if you want different sets of compiled files for the same
* templates. This is useful for things like different languages.
* Instead of creating separate sets of templates per language, you
* set different compile_ids like 'en' and 'de'.
*
* @var string
*/
var $compile_id = null;
Persistant compile identifier. As an alternative to passing the same $compile_id to each and every function call, you can set this $compile_id and it will be used implicitly thereafter.
With a $compile_id you can work around the limitation that you cannot use the same $compile_dir for different $template_dirs. If you set a distinct $compile_id for each $template_dir then Smarty can tell the compiled templates apart by their $compile_id.
If you have for example a prefilter that localizes your templates (that is: translates language dependend parts) at compile time, then you could use the current language as $compile_id and you will get a set of compiled templates for each language you use.
Another application would be to use the same compile directory across multiple domains / multiple virtual hosts.
上文的大致翻译
$compile_id
持续化的编译识别符。我们不用在每次函数调用时显式传递同一个$compile_id,而是可以设置该$compile_id,而它将被隐式调用。
使用$compile_id,你可以绕开对不同的$template_dirs不能使用相同的$compile_dir的限制。如果你对每个$template_dir赋予一个唯一的$compile_id,那么Smarty就可以根据它们的$compile_id来区别各个编译的模板。
例如,在编译时你有一个前过滤器以当地化你的模板(即:翻译与语种相关的部分),那么你就可以用当前语种作为$compile_id,从而对于每个你使用的语种,你将获得一套编译的模板。
另一个应用是,对于多域名/多虚拟主机使用相同的编译目录。
例子12-6. 虚拟主机环境下的$compile_id |
Example 12-6. $compile_id in a virtual host enviroment
|
关于smarty的cache_id和compile_id的说明
我一直对smarty的cache_id和compile_id有点混淆,总分不清有什么区别,好在以前没有遇到smarty的复杂应用,所以也就作罢了,不过这阵子一直在做多语言,多风格并存的UTF-8编码的网站,为了提高效率,决定使用smarty的缓存,就不得不好好看看了。对于我这个问题,很自然应该根据语言,风格(缓存组:language|theme)来缓存。那是放在cache_id里还是compile_id里呢?看看手册上对此的说明:
As an optional third parameter, you can pass a compile_id. This is in the event that you want to compile different versions of the same template, such as having separate templates compiled for different languages. Another use for compile_id is when you use more than one $template_dir but only one $compile_dir. Set a separate compile_id for each $template_dir, otherwise templates of the same name will overwrite each other. You can also set the $compile_id variable once instead of passing this to each call to this function.
这样看来,compile_id一般是用在你有多个template_dir但只有一个compile_dir,或者对同一个模板有不通的编译结果的情况下。比如showNews.php?newsId=123这样的情况,很自然的$_GET['newsId']应该作为compile_id存在。
简单来说$compile_id用于编译不同目录下的模板文件,以示区分生成的编译文件名,告诉Smarty你现在要编译哪个目录下的文件,主要用在$template_dir是一个以上目录的情况下
Smarty.class.php中的方法fetch中有如下的一行
$_smarty_compile_path = $this->_get_compile_path($resource_name);
然后方法_get_compile_path再调用方法_get_auto_filename方法,我们可以看到,_get_auto_filename的第三个参数就是$this->compile_id(也就是我们这儿所说的$compile_id),从 _get_auto_filename可以看到,编译文件名是跟参数$compile_id关联的,也就是说默认情况下一般不传$compile_id的时候$compile_id是空值,如果传入了$compile_id,则生成的编译文件名就与$compile_id关联起来了。
下面的前提是认为$compile_dir是同一个目录的情况下
1.现在假设某目录下有一个名为index.tpl.tml的模板文件,现在我们需要一套英文的模板、一套中文的模板,编译模板时,如果不传入$compile_id参数,则后一个生成的编译文件则覆盖前一个文件了,因为他们的文件名是相同的,所以如果你想让两个编译文件同时存在,则必须传入不同$compile_id参数,如en代表英文模板,cn代表中文模板。
2.现在假设a目录与b目录下均有一个名为index.tpl.tml的模板文件,如果不传入$compile_id参数,则后一个生成的编译文件则覆盖前一个文件了,因为他们的文件名是相同的,只是模板所在的目录名不相同而已。所以如果你想让两个编译文件同时存在,则必须传入$compile_id参数以示区分。
/**
* Get the compile path for this resource
*
* @param string $resource_name
* @return string results of {@link _get_auto_filename()}
*/
function _get_compile_path($resource_name)
{
return $this->_get_auto_filename($this->compile_dir, $resource_name,
$this->_compile_id) . '.php';
}
/**
* get a concrete filename for automagically created content
*
* @param string $auto_base
* @param string $auto_source
* @param string $auto_id
* @return string
* @staticvar string|null
* @staticvar string|null
*/
function _get_auto_filename($auto_base, $auto_source = null, $auto_id = null)
{
$_compile_dir_sep = $this->use_sub_dirs ? DIRECTORY_SEPARATOR : '^';
$_return = $auto_base . DIRECTORY_SEPARATOR;
if(isset($auto_id)) {
// make auto_id safe for directory names
$auto_id = str_replace('%7C',$_compile_dir_sep,(urlencode($auto_id)));
// split into separate directories
$_return .= $auto_id . $_compile_dir_sep;
}
if(isset($auto_source)) {
// make source name safe for filename
$_filename = urlencode(basename($auto_source));
$_crc32 = sprintf('%08X', crc32($auto_source));
// prepend %% to avoid name conflicts with
// with $params['auto_id'] names
$_crc32 = substr($_crc32, 0, 2) . $_compile_dir_sep .
substr($_crc32, 0, 3) . $_compile_dir_sep . $_crc32;
$_return .= '%%' . $_crc32 . '%%' . $_filename;
}
return $_return;
}