web-dev-qa-db-ja.com

PrimeFacesのプロセス/更新とJSFのf:ajax実行/レンダリング属性を理解する

PrimeFacesのp:commandXxxコンポーネントのprocessupdatef:ajaxタグのexecuterenderとは一体何なのでしょうか。

検証時にはどちらが機能しますか?バックエンドからコンポーネントの値を更新するのではなく、update属性が何をするのですか? process属性はモデルに値をバインドしますか? @this@parent@allおよび@formは、両方の属性で正確に何をしますか?

以下の例はうまくいっていますが、私は基本的な概念に少し混乱しています。

<p:commandButton process="@parent"
                 update="@form"
                 action="#{bean.submit}" 
                 value="Submit" />
170
Shardendu

<p:commandXxx process><p:ajax process><f:ajax execute>

process属性はサーバー側であり、 UIComponent の実装にのみ影響します EditableValueHolder (入力フィールド)または ActionSource (コマンドフィールド)。 process属性は、スペースで区切られたクライアントIDのリストを使用してJSFに伝えます。どのコンポーネントを(部分的な)フォーム送信時にJSFライフサイクル全体で正確に処理する必要があります。

次に、JSFは要求値を適用します(コンポーネントの独自のクライアントIDに基づいてHTTP要求パラメーターを見つけ、EditableValueHolderコンポーネントの場合は送信値として設定するか、ActionEventコンポーネントの場合は新しい ActionSource をキューに入れます)。変換、検証、およびモデル値の更新(EditableValueHolderコンポーネントのみ)を実行し、最後にキューに入れられたActionEventActionSourceコンポーネントのみ)を呼び出します。 JSFは、process属性でカバーされていない他のすべてのコンポーネントの処理をスキップします。また、要求値の適用フェーズ中にrendered属性がfalseに評価されるコンポーネントも、改ざんされた要求に対する保護の一部としてスキップされます。

ActionSourceコンポーネント(<p:commandButton>など)の場合、特にコンポーネントに関連付けられているアクションを呼び出す場合は、process属性にコンポーネント自体も含めることが非常に重要です。そのため、特定のコマンドコンポーネントが呼び出されたときに特定の入力コンポーネントのみを処理しようとする次の例は機能しません。

<p:inputText id="foo" value="#{bean.foo}" />
<p:commandButton process="foo" action="#{bean.action}" />

#{bean.foo}not#{bean.action}のみを処理します。コマンドコンポーネント自体も含める必要があります。

<p:inputText id="foo" value="#{bean.foo}" />
<p:commandButton process="@this foo" action="#{bean.action}" />

または、明らかに判明したように、共通の親を持つ唯一のコンポーネントである場合は@parentを使用します。

<p:panel><!-- Type doesn't matter, as long as it's a common parent. -->
    <p:inputText id="foo" value="#{bean.foo}" />
    <p:commandButton process="@parent" action="#{bean.action}" />
</p:panel>

または、両方が親 UIForm コンポーネントの唯一のコンポーネントである場合は、@formを使用することもできます。

<h:form>
    <p:inputText id="foo" value="#{bean.foo}" />
    <p:commandButton process="@form" action="#{bean.action}" />
</h:form>

これは、処理中にスキップしたい入力コンポーネントがフォームに含まれている場合、別の入力コンポーネントまたは現在の入力コンポーネントに基づいたUIセクションを更新する場合によくあることです。 Ajaxリスナーメソッド。つまり、他の入力コンポーネントの検証エラーがajaxリスナーメソッドの実行を妨げているのは望ましくありません。

次に、@allがあります。これはprocess属性では特別な効果はありませんが、update属性でのみ効果があります。 process="@all"は、process="@form"とまったく同じように動作します。とにかく、HTMLは一度に複数のフォームを送信することをサポートしません。

ちなみに@noneもありますが、これは絶対に何も処理する必要はないが、onlyupdateを介して特定の部分、特にコンテンツは送信された値やアクションリスナーに依存しません。

process属性は、HTTP要求ペイロード(要求パラメーターの量)にno影響を与えることに注意してください。つまり、<h:form>のHTML表現内に含まれる「すべて」を送信するデフォルトのHTML動作は影響を受けません。大きなフォームがあり、HTTPリクエストペイロードを処理に絶対に必要なもの、つまりprocess属性でカバーされるもののみに減らしたい場合は、<p:commandXxx ... partialSubmit="true">または<p:ajax ... partialSubmit="true">のようにPrimeFaces AjaxコンポーネントでpartialSubmit属性を設定できます。あるいは、この動作をデフォルトとするOmniFaces 3.0+の <o:form> を使用することもできます。

PrimeFaces固有のprocessと同等の標準JSFは、<f:ajax execute>executeです。 PrimeFacesがサポートしている間はコンマ区切りの文字列をサポートしていない(ただし、スペースで区切られた規則に従うことを個人的にお勧めします)こと、および@parentキーワードを除いて、まったく同じ動作をします。また、<p:commandXxx process>のデフォルトは@formであり、<p:ajax process>および<f:ajax execute>のデフォルトは@thisであることを知っておくと便利です。最後に、processがいわゆる「PrimeFacesセレクター」をサポートしていることを知っておくと便利です。 pdate = "@(。myClass)"のようにPrimeFacesセレクターはどのように機能しますか?


<p:commandXxx update><p:ajax update><f:ajax render>

update属性はクライアント側であり、すべてのUIComponentsのHTML表現に影響を与える可能性があります。 update属性は、スペースで区切られたクライアントIDのリストを使用して、JavaScript(ajaxリクエスト/レスポンスの処理を担当するもの)に通知します。HTMLDOMツリーのどの部分をフォーム送信に対する応答として更新する必要があります.

JSFは、そのための適切なajax応答を準備し、更新する要求された部分のみを含みます。 JSFは、ajax応答のupdate属性でカバーされていない他のすべてのコンポーネントをスキップし、応答ペイロードを小さく保ちます。また、レンダリング応答フェーズ中にrendered属性がfalseに評価されるコンポーネントはスキップされます。 trueを返しますが、最初にfalseだった場合、JavaScriptはHTML DOMツリーでそれを更新できないことに注意してください。代わりにラップするか、親を更新する必要があります。 Ajax update/renderは、レンダリングされた属性を持つコンポーネントでは機能しません も参照してください。

通常、onlyを更新する場合は、クライアント側でreallyに「リフレッシュ」する必要がある(部分的)フォーム送信。以下の例は、@formを介して親フォーム全体を更新します。

<h:form>
    <p:inputText id="foo" value="#{bean.foo}" required="true" />
    <p:message id="foo_m" for="foo" />
    <p:inputText id="bar" value="#{bean.bar}" required="true" />
    <p:message id="bar_m" for="bar" />
    <p:commandButton action="#{bean.action}" update="@form" />
</h:form>

process属性は省略されており、デフォルトでは既に@formになっているため注意してください)

これは正常に機能する可能性がありますが、この特定の例では、入力およびコマンドコンポーネントの更新は不要です。 fooメソッド内でモデル値barおよびactionを変更しない限り(UXパースペクティブでは直感的ではありません)、それらを更新する意味はありません。更新する必要があるreallyは、メッセージコンポーネントのみです。

<h:form>
    <p:inputText id="foo" value="#{bean.foo}" required="true" />
    <p:message id="foo_m" for="foo" />
    <p:inputText id="bar" value="#{bean.bar}" required="true" />
    <p:message id="bar_m" for="bar" />
    <p:commandButton action="#{bean.action}" update="foo_m bar_m" />
</h:form>

しかし、それらの多くを持っているとき、それは退屈になります。それがPrimeFaces Selectorsが存在する理由の1つです。これらのメッセージコンポーネントは、生成されたHTML出力にui-messageの共通スタイルクラスを持っているため、次のことも行う必要があります。

<h:form>
    <p:inputText id="foo" value="#{bean.foo}" required="true" />
    <p:message id="foo_m" for="foo" />
    <p:inputText id="bar" value="#{bean.bar}" required="true" />
    <p:message id="bar_m" for="bar" />
    <p:commandButton action="#{bean.action}" update="@(.ui-message)" />
</h:form>

(メッセージコンポーネントのIDを保持する必要があることに注意してください。そうしないと、@(...)は機能しません! pdate = "@(。myClass)"のようにPrimeFacesセレクターはどのように機能しますか? 詳細)

@parentは親コンポーネントのみを更新するため、現在のコンポーネントとすべての兄弟とその子がカバーされます。フォームが適切なグループに分かれており、それぞれが独自の責任を負っている場合に便利です。 @thisは、明らかに現在のコンポーネントのみを更新します。通常、これはアクションメソッドでコンポーネントのHTML属性の1つを変更する必要がある場合にのみ必要です。例えば。

<p:commandButton action="#{bean.action}" update="@this" 
    oncomplete="doSomething('#{bean.value}')" />

oncompleteは、valueで変更されるactionで動作する必要があると想像してください。oncompleteが生成されたHTML出力の一部であるという単純な理由により、コンポーネントが更新されない場合、このコンストラクトは機能しませんでした(したがって、すべてのEL式レンダリング応答中に評価されます)。

@allはドキュメント全体を更新するため、注意して使用する必要があります。通常、プレーンリンク(<a>または<h:link>)または?faces-redirect=trueまたはExternalContext#redirect()によるPOST後のリダイレクトのいずれかによって、これに対して真のGETリクエストを使用します。エフェクトでは、process="@form" update="@all"には、非ajax(非部分)の送信とまったく同じ効果があります。私のJSFのキャリア全体で、@allで遭遇した唯一の実用的なユースケースは、ajaxリクエスト中に例外が発生した場合にエラーページ全体を表示することです。 AJAXifiedコンポーネントのJSF 2.0例外に対処する正しい方法は何ですか?

PrimeFaces固有のupdateと同等の標準JSFは、<f:ajax render>renderです。 PrimeFacesがサポートしている間はコンマ区切りの文字列をサポートしていない(ただし、スペースで区切られた規則に従うことを個人的にお勧めします)こと、および@parentキーワードを除き、まったく同じ動作をします。 updaterenderのデフォルトは、@none(つまり、「nothing」)です。


以下も参照してください:

277
BalusC

デフォルト値を覚えているのに苦労しているなら(私は知っている...)BalusCの答えからの抜粋がここにあります。

コンポーネント|送信する更新
 ------------ | --------------- | -------------- 
 f:ajax | execute = "@ this" | render = "@ none" 
 p:ajax | process = "@ this" | update = "@ none" 
 p:command XXX | process = "@ form" | update = "@ none" 
49
Jaqen H'ghar

プロセスごとに(JSF仕様ではexecuteと呼ばれます)、JSFに処理をコンポーネントに限定するように指示します。それ以外のものは無視されます。

updateは、サーバーがユーザーの要求に応答したときにどの要素が更新されるかを示します。

@all :すべてのコンポーネントは処理/レンダリングされます。

@this :実行属性を持つ要求側コンポーネントが処理/レンダリングされます。

@form :要求元のコンポーネントを含むフォームが処理/レンダリングされます。

@parent :要求元コンポーネントを含む親が処理/レンダリングされます。

Primefacesを使えば、JQueryセレクターを使うこともできます。このブログをチェックしてください: http://blog.primefaces.org/?p=1867

23
faissalb