Thursday, August 14, 2008

Сжатие вывода Smarty

У smarty есть возможность установить пользововательские фильтры для выводимого содержимого через register_outputfilter(). Например так можно сжать страницу:
...
$smarty->register_outputfilter('output_compress');
...
function output_compress($tpl_output, &$smarty)
{
if(headers_sent()) return $tpl_output;
header('Content-Encoding: deflate');
return gzdeflate($tpl_output, 4);
}

Но если при выполнении кода случится вывод Warning (т.е. display_errors = On), то вы не получите ожидаемого результата (Firefox 3 ругается на неподдерживаемый метод сжатия), т.к. текст этого предупреждения не попадает в $tpl_output и остается в буфере. В результате, на выходе часть содержимого будет не сжата, а заголовок сжатия будет послан.

Чтобы избежать этого, использую такой подход:
...
function output_compress($tpl_output, &$smarty)
{
if(headers_sent()) return $tpl_output;
if($t = ob_get_contents()) {
$tpl_output = $t . $tpl_output;
ob_clean();
}
header('Content-Encoding: deflate');
return gzdeflate($tpl_output, 4);
}