Smarty Forum Index Smarty
WARNING: All discussion is moving to https://reddit.com/r/smarty, please go there! This forum will be closing soon.

Gzipping of cached templates.

 
This forum is locked: you cannot post, reply to, or edit topics.   This topic is locked: you cannot edit posts or make replies.    Smarty Forum Index -> Tips and Tricks
View previous topic :: View next topic  
Author Message
electr0`n
Guest





PostPosted: Fri May 07, 2004 12:22 pm    Post subject: Gzipping of cached templates. Reply with quote

If your templates are very large, the cached template are also large. If you don't want to waste your webspace, you can gzip your cached templates and reduce the needed webspace.
I've tested the performance and It's not much slower than normal caching.

core/core.read_cache_file.php
[php:1:ea5744576b]<?php
/**
* Smarty plugin
* @package Smarty
* @subpackage plugins
*/

/**
* read a cache file, determine if it needs to be
* regenerated or not
*
* @param string $tpl_file
* @param string $cache_id
* @param string $compile_id
* @param string $results
* @return boolean
*/

// $tpl_file, $cache_id, $compile_id, &$results

function smarty_core_read_cache_file(&$params, &$smarty)
{
static $content_cache = array();

if ($smarty->force_compile) {
// force compile enabled, always regenerate
return false;
}

if (isset($content_cache[$params['tpl_file'].','.$params['cache_id'].','.$params['compile_id']])) {
list($params['results'], $smarty->_cache_info) = $content_cache[$params['tpl_file'].','.$params['cache_id'].','.$params['compile_id']];
return true;
}

if (!empty($smarty->cache_handler_func)) {
// use cache_handler function
call_user_func_array($smarty->cache_handler_func,
array('read', &$smarty, &$params['results'], $params['tpl_file'], $params['cache_id'], $params['compile_id'], null));
} else {
// use local cache file
$_auto_id = $smarty->_get_auto_id($params['cache_id'], $params['compile_id']);
$_cache_file = $smarty->_get_auto_filename($smarty->cache_dir, $params['tpl_file'], $_auto_id);
$params['results'] = $smarty->_read_file($_cache_file);
}

if (empty($params['results'])) {
// nothing to parse (error?), regenerate cache
return false;
}

$cache_split = explode("\n", $params['results'], 2);
$cache_header = $cache_split[0];

$_cache_info = unserialize($cache_header);

if ($smarty->caching == 2 && isset ($_cache_info['expires'])){
// caching by expiration time
if ($_cache_info['expires'] > -1 && (time() > $_cache_info['expires'])) {
// cache expired, regenerate
return false;
}
} else {
// caching by lifetime
if ($smarty->cache_lifetime > -1 && (time() - $_cache_info['timestamp'] > $smarty->cache_lifetime)) {
// cache expired, regenerate
return false;
}
}

if ($smarty->compile_check) {
$_params = array('get_source' => false, 'quiet'=>true);
foreach (array_keys($_cache_info['template']) as $_template_dep) {
$_params['resource_name'] = $_template_dep;
if (!$smarty->_fetch_resource_info($_params) || $_cache_info['timestamp'] < $_params['resource_timestamp']) {
// template file has changed, regenerate cache
return false;
}
}

if (isset($_cache_info['config'])) {
$_params = array('resource_base_path' => $smarty->config_dir, 'get_source' => false, 'quiet'=>true);
foreach (array_keys($_cache_info['config']) as $_config_dep) {
$_params['resource_name'] = $_config_dep;
if (!$smarty->_fetch_resource_info($_params) || $_cache_info['timestamp'] < $_params['resource_timestamp']) {
// config file has changed, regenerate cache
return false;
}
}
}
}

foreach ($_cache_info['cache_serials'] as $_include_file_path=>$_cache_serial) {
if (empty($smarty->_cache_serials[$_include_file_path])) {
$smarty->_include($_include_file_path, true);
}

if ($smarty->_cache_serials[$_include_file_path] != $_cache_serial) {
/* regenerate */
return false;
}
}

/* uncompress the template content */
$params['results'] = gzuncompress($cache_split[1]);
$content_cache[$params['tpl_file'].','.$params['cache_id'].','.$params['compile_id']] = array($params['results'], $_cache_info);

$smarty->_cache_info = $_cache_info;
return true;
}

/* vim: set expandtab: */

?>
[/php:1:ea5744576b]
core/core.write_cache_file.php
[php:1:ea5744576b]<?php
/**
* Smarty plugin
* @package Smarty
* @subpackage plugins
*/

/**
* Prepend the cache information to the cache file
* and write it
*
* @param string $tpl_file
* @param string $cache_id
* @param string $compile_id
* @param string $results
* @return true|null
*/

// $tpl_file, $cache_id, $compile_id, $results

function smarty_core_write_cache_file($params, &$smarty)
{

// put timestamp in cache header
$smarty->_cache_info['timestamp'] = time();
if ($smarty->cache_lifetime > -1){
// expiration set
$smarty->_cache_info['expires'] = $smarty->_cache_info['timestamp'] + $smarty->cache_lifetime;
} else {
// cache will never expire
$smarty->_cache_info['expires'] = -1;
}

// collapse {nocache...}-tags
$params['results'] = preg_replace('!((\{nocache\:([0-9a-f]{32})#(\d+)\})'
.'.*'
.'{/nocache\:\\3#\\4\})!Us'
,'\\2'
,$params['results']);
$smarty->_cache_info['cache_serials'] = $smarty->_cache_serials;

/* compress with gzip */
$params['results'] = gzcompress($params['results']);

// prepend the cache header info into cache file
$params['results'] = serialize($smarty->_cache_info)."\n".$params['results'];

if (!empty($smarty->cache_handler_func)) {
// use cache_handler function
call_user_func_array($smarty->cache_handler_func,
array('write', &$smarty, &$params['results'], $params['tpl_file'], $params['cache_id'], $params['compile_id'], null));
} else {
// use local cache file

if(!@is_writable($smarty->cache_dir)) {
// cache_dir not writable, see if it exists
if(!@is_dir($smarty->cache_dir)) {
$smarty->trigger_error('the $cache_dir \'' . $smarty->cache_dir . '\' does not exist, or is not a directory.', E_USER_ERROR);
return false;
}
$smarty->trigger_error('unable to write to $cache_dir \'' . realpath($smarty->cache_dir) . '\'. Be sure $cache_dir is writable by the web server user.', E_USER_ERROR);
return false;
}

$_auto_id = $smarty->_get_auto_id($params['cache_id'], $params['compile_id']);
$_cache_file = $smarty->_get_auto_filename($smarty->cache_dir, $params['tpl_file'], $_auto_id);
$_params = array('filename' => $_cache_file, 'contents' => $params['results'], 'create_dirs' => true);
require_once(SMARTY_DIR . 'core' . DIRECTORY_SEPARATOR . 'core.write_file.php');
smarty_core_write_file($_params, $smarty);
return true;
}
}

/* vim: set expandtab: */

?>
[/php:1:ea5744576b]
Back to top
boots
Administrator


Joined: 16 Apr 2003
Posts: 5611
Location: Toronto, Canada

PostPosted: Fri May 07, 2004 6:36 pm    Post subject: Reply with quote

hmm. I don't know if I'd bother with this using the standard file based caching as I'm paying less than a dollar per Gigabyte of storage. On the-other-hand, this is cool if you are using the mmcache handler for shared memory content caching.

nice.
Back to top
View user's profile Send private message
electr0`n
Guest





PostPosted: Sat May 08, 2004 4:00 pm    Post subject: Reply with quote

boots wrote:
hmm. I don't know if I'd bother with this using the standard file based caching as I'm paying less than a dollar per Gigabyte of storage. On the-other-hand, this is cool if you are using the mmcache handler for shared memory content caching.

If you're using a Zend-Engine Cache you mostly have a server and enough space Very Happy
boots wrote:
nice.

thx
Back to top
markon
Smarty Rookie


Joined: 11 Jun 2004
Posts: 6
Location: Czech Republic

PostPosted: Fri Jun 18, 2004 7:24 am    Post subject: It's usefull Reply with quote

I thing it's cool

Quote:

You need some time to compress webpage

, but Very Happy

Quote:

In real enviroment, it's safe time spend by saving results to hard drive


In fact, I found many times, the compress time it's not important, but hdd access time it's much more important. Cache results can be perfectly compressed by ratio 1:5, and there is really difference between saving 100kB of data or saving 20kB of data.
_________________
--markon
Back to top
View user's profile Send private message Visit poster's website
messju
Administrator


Joined: 16 Apr 2003
Posts: 3336
Location: Oldenburg, Germany

PostPosted: Fri Jun 18, 2004 8:51 am    Post subject: Reply with quote

maybe it's worth benchmarking and comparing.

but why did you (electr0`n) hack up the core for that instead of using $smarty->cache_handler_func?
Back to top
View user's profile Send private message Send e-mail Visit poster's website
electr0n
Smarty Rookie


Joined: 26 Mar 2004
Posts: 32
Location: Germany

PostPosted: Fri Jun 18, 2004 1:16 pm    Post subject: Reply with quote

messju wrote:
maybe it's worth benchmarking and comparing.

but why did you (electr0`n) hack up the core for that instead of using $smarty->cache_handler_func?

Hacking the core was in this case less work, than write a cache handler (I'm so lazy Very Happy).

markon wrote:

In fact, I found many times, the compress time it's not important, but hdd access time it's much more important.

Ok, but I needed this, because my cached templates are very big.
Back to top
View user's profile Send private message
electr0n
Smarty Rookie


Joined: 26 Mar 2004
Posts: 32
Location: Germany

PostPosted: Sat Jun 19, 2004 12:02 pm    Post subject: Reply with quote

[php:1:01fa708822]<?php
/**
* a gzip-cache handler for smarty
*
* @access private
* @return boolean
*
* @param string $method
* @param object $smarty
* @param string $cache_content
* @param string $template_file
* @param string $cache_id
* @param string $compile_id
*/
function smarty_gzip_cache_handler($method, &$smarty, &$cache_content, $template_file = '', $cache_id = '', $compile_id = '')
{
if (!empty($template_file)) {
$auto_id = $smarty->_get_auto_id($cache_id, $compile_id);
$cache_file = $smarty->_get_auto_filename($smarty->cache_dir, $template_file, $auto_id);
}

switch ($method) {
case 'clear':
if (empty($template_file) && empty($cache_id) && empty($compile_id)) {
$handle = opendir($this->cache_dir);
while ($file = readdir($handle)) {
unlink($smarty->cache_dir . DIRECTORY_SEPARATOR . $file);
}
closedir($handle);
} else {
unlink($cache_file);
}
break;

case 'read':
if ($cache_content = $smarty->_read_file($cache_file)) {
$cache_content = gzuncompress($cache_content);
} else {
$cache_content = '';
}
break;

case 'write':
$params = array(
'filename' => $cache_file,
'contents' => gzcompress($cache_content),
'create_dirs' => TRUE
);
require_once(SMARTY_DIR . 'core' . DIRECTORY_SEPARATOR . 'core.write_file.php');
smarty_core_write_file($params, $smarty);
break;
}

return TRUE;
}
?>[/php:1:01fa708822]
Back to top
View user's profile Send private message
markon
Smarty Rookie


Joined: 11 Jun 2004
Posts: 6
Location: Czech Republic

PostPosted: Sat Jun 19, 2004 4:09 pm    Post subject: Nice, but doesn't support cache expire time (repaired) Reply with quote

Your plug-in doesn't support cache expire time and doesn't work properly when you try to clean cache (I get message 'permission denied', but in Smarty I never get this).

I make some modification to work properly.
[php:1:8a52375e21]<?php
function smarty_gzip_cache_handler($method, &$smarty, &$cache_content, $template_file = '', $cache_id = '', $compile_id = '', $exp_time=null)
{
if (!empty($template_file)) {
$auto_id = $smarty->_get_auto_id($cache_id, $compile_id);
$cache_file = $smarty->_get_auto_filename($smarty->cache_dir, $template_file, $auto_id);
}

switch ($method) {
case 'clear':
// Changed
unset($smarty->cache_handler_func);
$smarty->clear_all_cache($exp_time);
$smarty->cache_handler_func='smarty_gzip_cache_handler';
// Changed
break;

case 'read':
if ($cache_content = $smarty->_read_file($cache_file)) {
$cache_content = gzuncompress($cache_content);
} else {
$cache_content = '';
}
break;

case 'write':
$params = array(
'filename' => $cache_file,
'contents' => gzcompress($cache_content),
'create_dirs' => TRUE
);
require_once(SMARTY_DIR . 'core' . DIRECTORY_SEPARATOR . 'core.write_file.php');
smarty_core_write_file($params, $smarty);
break;
}

return TRUE;
}
?>[/php:1:8a52375e21][/code]
_________________
--markon
Back to top
View user's profile Send private message Visit poster's website
boots
Administrator


Joined: 16 Apr 2003
Posts: 5611
Location: Toronto, Canada

PostPosted: Sat Jun 19, 2004 4:41 pm    Post subject: Reply with quote

or consider combining it with one of the mmcache handlers:

http://www.phpinsider.com/smarty-forum/viewtopic.php?t=1507&highlight=mmcache
Back to top
View user's profile Send private message
electr0n
Smarty Rookie


Joined: 26 Mar 2004
Posts: 32
Location: Germany

PostPosted: Sat Jun 19, 2004 5:51 pm    Post subject: Reply with quote

Thanks for the tipps markon!
Back to top
View user's profile Send private message
Display posts from previous:   
This forum is locked: you cannot post, reply to, or edit topics.   This topic is locked: you cannot edit posts or make replies.    Smarty Forum Index -> Tips and Tricks All times are GMT
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2005 phpBB Group
Protected by Anti-Spam ACP