7.7. Události v životním cyklu aplikace

Během zpracování událostí v životním cyklu mohou být volány některé metody třídy FacesContext, které přeruší či zkrátí cyklus.

Přerušení může nastat voláním metody responseComplete(), která se použije v případě, že požadavek byl přesměrován na jiný zdroj a JSF se již nemusí o odpověď starat. Může se jednat např. o situaci, kdy je uživatel přesměrován na obyčejnou HTML stránku bez JSF elementů, či na soubor, který má být stažen atp. Tato možnost je na obrázku 7.2 znázorněna šipkami s popiskem "Response Complete".

Zkrácení životního cyklu lze provést metodou renderResponse(), kterou byla zmíněna již výše v souvislosti s Initial Requestem. Metoda zajistí násilné přeskočení zbývajících fází a přikročí rovnou k fázi Render Response. Tato možnost je na obrázku 7.2 znázorněna šipkami s popiskem "Render Response". Zkrácení cyklu se používá například v souvislosti s atributem immediate, který jsem zmínil v sekci 4.3.1 – „Základní atributy tagů“.

7.7.1. Ovlivňování životního cyklu pomocí atributu immediate

Za normálních okolností jsou akce typu value-changed events zpracovávány ve fázi Process Validations a akce typu action events ve fázi Invoke Application, což je většinou žádoucí chování [3]. Někdy však můžeme potřebovat validaci uspíšit, nebo přeskočit a k tomu slouží právě atribut immediate, který dokáže ovlivnit, v jaké fázi budou akce zpracovávány. Můžeme ho použít buď u UIInput, nebo u UICommand komponent.

7.7.1.1. UICommand komponenty s atributem immediate

Může nastat situace, kdy potřebujete konverzi a validaci přeskočit. Představte si například formulář, kde máte jedno pole s atributem required nastaveným na hodnotu true a na konci formuláře je kromě tlačítka Potvrdit také tlačítko Zrušit, které uživatele vrací třeba na předchozí stránku. Pokud by chtěl uživatel využít tlačítko Zrušit, nemá smysl vyžadovat po něm vyplnění povinných polí.

Pro tento případ se nám hodí atribut immediate. Nastavení tohoto atributu na hodnotu true zajistí, že akce vyvolaná tlačítkem bude zpracována již po fázi Apply Request Values. Hned nato je zpracována akce, která řídí navigaci a automaticky volá metodu renderResponse(). Zpracování události tak proběhne ještě před procesy konverze a validace a uživatel bude bez problémů přesměrován na požadovanou stránku.

Příklad 7.1. Využití atributu immediate u UICommand komponenty

<h:inputText id="vek" value="#{objednavka.cena}" required="true"/><br/>
<h:commandButton value="Potvrdit" action="success"/>
<h:commandButton value="Zrušit" action="cancel" immediate="true"/>

7.7.1.2. UIInput komponenty s atributem immediate

Nyní si vzpomeňte na příklad 6.5, kde jsme měli combobox s atributem onchange, jenž volal metodu submit(). Tato metoda na straně klienta zajišťuje potvrzení formuláře ihned po změně hodnoty. Představte si, že součástí formuláře je také povinné textové pole, jehož vyplnění však chcete kontrolovat, jen pokud je stisknuto potvrzovací tlačítko, nikoli při změně hodnoty comboboxu.

V tom případě nastavíte tagu comboboxu atribut immediate na true, čímž zajistíte, že jeho konverze a validace proběhne již ve fázi Apply Request Values a hned nato bude vyhozena událost value-changed event. Situace je zde však o něco složitější, než u UICommand komponenty. Zde totiž není volána metoda renderResponse() automaticky a za normálních okolností by následně proběhla konverze a validace všech ostatních polí. Pokud se tomu chcete vyhnout, musíte zavolat metodu renderResponse() sami ve vašem listeneru.

Příklad 7.2. Využití atributu immediate u UIInput komponenty

<h:selectOneMenu value="#{objednavka.mena}" onchange="submit()" immediate="true">
    <f:valueChangeListener type="beany.zmenaMeny"/>
    <f:selectItems value="#{objednavka.meny}"/>
</h:selectOneMenu>

Do listeneru byste pak museli přidat volání metody renderResponse() - FacesContext.getCurrentInstance().renderResponse(); (pro více informací o třídě FacesContext a jejich metodách viz [6]).

Creative Commons License
Uvedená práce (dílo), jejímž autorem je Bc. David Hanel, podléhá licenci Creative Commons Uveďte autora-Neužívejte dílo komerčně-Zachovejte licenci 3.0 Česko.