Odeslani odpovedi az po zpracovani cele sablony (ještě jednou

Upozornění: Tohle vlákno je hodně staré a informace nemusí být platné pro současné Nette.
setka
Člen | 10
+
0
-

Chtěl bych navázat na už uzavřené téma: https://forum.nette.org/…cele-sablony

Potřebuji dosáhnou chování, které je tam popsáno. Jde mi o ErrorPresenter, kterým v produkčním prostředí generuji hezké stránky s popisem chyby 404 / 500 atd.

Protože mám některé komponenty, které mohou vyvolat výjimku v render fázi, stává se mi, že se ta chybová stránka včetně HTML hlavičky vloží někam doprostřed zpola vygenerované původní stránky (vím, že vyhazovat výjimky v renderu není úplně čisté, ale mám to jen na pár místech, kde to má dost dobrý důvod). Řešením je ten zmiňovaný output_buffering. Ale tohle (citace z odkazovaného tématu):

Druhou možností je globální nastavení v config.ini (viz manuál):

[common]
php.implicit_flush = false
php.output_buffering = on

Nefunguje, protože output_buffering nelze nastavovat přes ini_set, viz: http://www.php.net/…guration.php kde je output_buffering jako PHP_INI_PERDIR, tzn. že to jde měnit jen v php.ini nebo přes .htaccess (ale to samozřejmě jen pro mod_php). On ini_set v takovém případě ani nevyhodí chybu, resp. Nette to možná nekontroluje. implicit_flush je potřeba také, ale ten přes ini_set jde.

Po doplnění ob_start() do bootstrapu, a přidání mazání output bufferu do ErrorPresenteru:

<?php
class Front_ErrorPresenter extends BasePresenter
{
  public function renderDefault($exception)
  {
    ...
    // clear output buffer (inspired by Nette\Debug::processException()
    if(!headers_sent())
    {
      @ob_end_clean();
      while (ob_get_level() && @ob_end_clean());

      if(in_array('Content-Encoding: gzip', headers_list()))
      {
        header('Content-Encoding: identity', TRUE); // override gzhandler
      }
    }
  }
}
?>

vše funguje tak jak bych si představoval. Nestálo by za to integrovat tuhle funkcionalitu do Nette pomocí nějaké konfigurační volby? Může prosté přidání ob_start() na konec bootstrapu před ->run() způsobit nějaký problém? Bylo by lepší to dát jinam?

Editoval setka (6. 7. 2010 19:19)

toka
Člen | 253
+
0
-

?

setka
Člen | 10
+
0
-

toka napsal(a):

?

Omlouvám se. Nejdřív jsem si omylem zavřel v prohlížeči panel, kde jsem to popsal mnohem podrobněji. Pak jsem ve vzteku při novém zakládání vlákna v políčku s nadpisem zmáčknul enter, a už s tím nešlo nic dělat.

PS.: U uzavřených vláken není vidět odkaz „Citace“ a tady jsem ho zrovna potřeboval.

David Grudl
Nette Core | 8228
+
0
-

Věc se má tak, že průměrná nezkomprimovaná HTML stránka má 100kB – 200kB (dle nějakého výzkumu Google). V tomto rozsahu může vyletět výjimka, třeba i kvůli snaze odeslat HTTP hlavičku. Jak velký buffer použít, aby se dal odstranit úspěšně vyčistit? 100% spolehlivý bude jen 100% buffer, tedy zavolat na začátku ob_start() a odesílat stránku až po kompletním vyrenderování. Pak se ale bude zdát, že server reaguje pomalu.

Určitým kompromisem, se kterým experimentuju, je buffer, který není limitovaný velikostí, ale časem. Bufferuje vše prvních cca 200ms. Dobře to řeší standardní jednodušší stránky.

Stále tu ale není jistota, že se podaří zahodit celý výstup. Proto by možná bylo lepší řešení na úrovni CSS, které by výstup obalený třeba do divu id=„wrapper“ skrylo a nahradilo chybovou hláškou.