Maximum execution time exceeded – NRecursiveDirectoryIteratorFixed

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

Ahoj,

na jednom starsim projektu pouzivam Nette vicemene jen ke kesovani, ale narazim posledni dobou stale casteji na maximum execution time exceeded. To by samo o sobe nebylo nic divnyho, protoze server ve spickach nestiha, ale v 90% konci na tride NRecursiveDirectoryIteratorFixed.

Nemel nekdo podobny problem? Predpokladam, ze se jedna o problem prave pri prochazeni kese, protoze souboru je v jednom storage asi 100tis., ale at zkousim cokoliv, nemuzu to nijak vyresit.

Pouzivam v2.0.7

Diky za kazdy tip

enumag
Člen | 2118
+
0
-

Co je to za storage, že je tam tolik souborů? Nějaká část Nette nebo něco nesouvisejícího?

kuty.cz
Člen | 33
+
0
-

soubory samotne kese… mam v jedne tabulce priblizne 100tis. polozek a k tem se z ruznych zdroju (jine DB, LDAP..) datahuji dalsi informace a neco se i pocita.

Vetsinou se zobrazuje v prumeru 100 polozek, ale i presto by byl vypocet pokazde casove narocny, takze proto se to kesuje a dodatecne informace se nacitaji z kese, ktera se invaliduje po urcitym timeoutu.

enumag
Člen | 2118
+
0
-

Při takovém množství se ani moc nedivím, že to trvá tak dlouho… Řešení:

  1. Neinvalidovat v závislosti na čase, místo toho přidej tagy. Ty tagy mohou být např. datum.
  2. Vytvoř cron, který vždy invaliduje nějaké už neplatné tagy. Informace který záznam patří kterému tagu je myslím uložená v journalu takže by nemělo být potřeba procházet všechny soubory v cache jako nyní, což by mělo být mnohem rychlejší. Stejně bych to ale raději invalidoval cronem než při standardním požadavku.
kuty.cz
Člen | 33
+
0
-

Zkousel jsem i invalidaci pri zmene a vyhodit uplne invalidaci casovou, ale reseni to nebylo.

Podle toho co radis je podle Tebe chyba v tom, ze se nette, resp. garbage collector prochazi vsechny soubory cache a tim to zaseka?

mkoubik
Člen | 728
+
0
-

Filestorage je na tohle asi moc pomalej. Pokud je to aspoň trochu možné (vlastní server), tak zkus použít redis. Ten by to měl zvládat v řádu milisekund.

enumag
Člen | 2118
+
0
-

Nette s určitou pravděpodobností maže všechny již nevalidní záznamy. A tehdy musí samozřejmě každý soubor po jednom projít (každý záznam má v sobě uvedeny závislosti). Přitom se to právě zasekne. Teď když koukám na implementaci, tak to ještě trochu upřesním:

  1. Je třeba zajistit aby se na daném storage nikdy nespouštěla metoda clean(). Tedy jednak ji nesmíš spouštět sám a druhak musíš výše zmíněnou pravděpodobnost nastavit na 0.
  2. Invalidace pomocí tagů soubory skutečně neprochází, takže když budeš invalidovat přes journal, mělo by to být ok:
// $journal získáš z DI containeru
/** @var $journal \Nette\Caching\Storages\IJournal */
$journal->clean(array(Cache::TAGS => /* pole tagů ke smazání */));

EDIT: S redisem zkušenosti nemám, dej vědět jak to dopadne pokud ho zkusíš. ;-)

Editoval enumag (10. 1. 2013 10:18)

kuty.cz
Člen | 33
+
0
-

diky za rady, urcite vyzkousim.. momentalne zkousim jet bez cache abych vyloucil, ze problem neni jinde, ale vypada to, ze opravdu bude problem to mnozstvi souboru..