2011-08-25 4 views
11

私のJSF/RichFaces/Facelets ajaxリクエストのパフォーマンスに問題があります。コンポーネントツリー全体が各Ajaxリクエストで再構築されているため、私はそれを知ることができます。これは、ajaxSingle = true、a4j:regionのセクションを折り返し、再レンダリングのためのセクションを宣言したり、まったく宣言しない場合でも発生します。私たちのページは、多くの入れ子レベルを持つダイナミックなページです。ページには約800-900のフィールド(inputText、豊富なカレンダー、selectOneMenusなど)が含まれている場合があります。最初の読み込み時間は問題ですが、私はその問題を理解しています、その多くのフィールド。初期のビルド/レンダリング時間を取得したら、他のすべてのアクションをajaxに設計し、必要なものだけを再レンダリングします。私はAJAX呼び出しにこのようなメッセージが表示さFaceletsのデバッグログから:各AjaxリクエストでJSFビューを再構築する

2011-08-24 22:19:03,054 DEBUG [facelets.viewhandler] (http-0.0.0.0-8080-2) Took 
24445ms to build view: /oconsole/appfile.xhtml 
2011-08-24 22:19:09,377 DEBUG [facelets.viewhandler] (http-0.0.0.0-8080-2) Took 
6323ms to render view: /oconsole/appfile.xhtml 

私は、我々がやっている何かが全体のコンポーネントツリー、またはFaceletsを再構築は、いくつかのために必要な、この必要性を決定している原因となっているかどうかわからないんだけど理由(古いキャッシュ?)。ここに私たちのスタックがあります: JBoss 5.1 JSF 1.2 RichFaces。 - facelets.BUILD_BEFORE_RESTORE = falseを facelets.REFRESH_PERIOD =:私は、彼らが助けになるかどうかを確認するために、いくつかのコンテキストパラメータを追加しようとしているが、彼らは何もしなかった3.3.3.Final Faceletsの1.1.15 シーム2.1.2

1または5(5分以内)

私たちのビューが正しくキャッシュされているかどうかを確認するにはどうしますか?状態を保存する方法をデリケートしないので、サーバー側にデフォルト設定されていると思います。私たちのすべての要求は、シームの長い会話の中で起こります。ビューがセッションレベルでキャッシュされると思ったので、これが要因であるかどうかはわかりませんでしたか?どんな助けでも大歓迎です、ありがとうございます。よりデバッグ後

更新:(FaceletsViewHandlerのメンバ変数を持つ)

AjaxViewHandlerはdevelopmentMode =真のセットを有しています。フェイスレットがビューをキャッシュしないようにしている場合、開発サイクル中に変更がリフレッシュされるかどうかはわかりません。 Facelets/JSFのビューとその動作のキャッシングに関する情報を見つけることは非常に困難でした。さらに、コンフィグパラメータを追加すると:

<context-param> 
<param-name>facelets.DEVELOPMENT</param-name> 
<param-value>false</param-value> 
</context-param> 

これはかかりませんでした。デバッガでは、私はまだ真のセットを見ています。私たちにはサブビューがたくさんあるので、私も com.sun.faces.numberOfLogicalViewsと com.sun.faces.numberOfViewsInSession から15(デフォルト)の1000にアップしました。これは効果がありませんでした。

私はまた、クライアント側の状態の保存に幸運なしに変更しようとしました。アイデアの不足....

....誰かが助けることができることを望むシーム2.1 RichFacesのを自動的に初期化しそうですし、それはそれとは何か.....

+0

これは古い質問ですが、多くの分野でこれを検討することがあります:http://industrieit.com/blog/2011/11/stateless-jsf-high-performance-zero-per -request-memory-overhead/ –

答えて

5
を持っている場合、私はわからないんだけど

パフォーマンスの問題と同様に、プロファイラはボトルネックの特定に大きく役立ちます。 (はい、それはrestore_viewフェーズですが、restore_viewフェーズのどこにあるのかわかりません)。つまり、復元ビューのフェーズでは、処理またはレンダリングされる部分だけでなく、ビュー全体が復元されます。

プロセス:ID [ 'S](コールUIComponent.findComponent(の形式で))の成分の、この成分によるAjaxRequestの場合には位相2-5で処理RichFaces taglib documentationを引用。

再レンダリング:配列またはコレクションを持つ単一のIDはIDのカンマで区切ったリスト、またはEL式を使用でき

RESTORE_VIEWはまた、フェーズ1であるID [さん](呼び出しの形式でUIComponent.findComponent())。このコンポーネントによって引き起こされたAjaxRequestの場合にレンダリングされます。独身IDののID、カンマ区切りのリスト、またはEL式が配列またはコレクションにすることができ

また、私はUIComponent.findComponentは()コンポーネントツリーよりも適してデータ構造を使用して実装されていることを確認していません。 (コンポーネントツリー内の何かを見つけることは、線形検索に沸き起こるでしょう...)。

私はJSF 2.0(Mojarra)で同様の効果が見られました。私の結論は、ビューがレンダリングされているかどうかにかかわらず、ビューには数十ものUIComponentが含まれてはならないということでした。 (別の言い方をすれば、AJAXはページのナビゲーションには適していません)。ビューに現在表示されているコンポーネントだけを含めることでビューを小さく保つことができます。つまり、1つのビューに10個のタブがあり、それぞれに30個のコンポーネントがある場合は、10個のビューがあり、それぞれには1つのタブのコンテンツしか含まれていません。そのアプローチの欠点は、タブを切り替えるときにコンポーネントが配置され、バッキングビーンに保持されていない状態が失われることです。

私はこれが良い解決策であると主張していません。悲しいかな、それは数週間前にこれを調べるときに私が見つけた最高のものでした。私はより良いものを見せてくれることを嬉しく思います。

編集 私が復元言うとき、私は最初のget要求とポストバックのために両方とも呼ばViewHandler.restoreView()を意味します。 restoreViewは、既存のビューをそのまま再利用すると言っても間違いです。例えば、セクション7.6.2.7でJSF 2.0仕様の義務:]

restoreView()方法は、以下の責任を果たす必要があります。

すべて実装しなければならない:

  • 何らのviewIdが特定できなかった場合、返品null
  • 現在の要求と計算のviewIdためFacesContextインスタンスを渡し、関連StateManagerrestoreView()メソッドを呼び出し、そしてnullであってもよい戻さUIViewRootを返します。

およびセクション7.7.2で:

JSF実装(セクション11.1を参照 javax.faces.STATE_SAVING_METHOD初期化パラメータの値に基づいて、状態を保存するための2つの主要メカニズムをサポートします。 3「アプリケーション構成 パラメータ」を参照してください)。このパラメータの可能な値に使用するアプローチの一般的な指標を与える、技術的な詳細に革新を JSF実装を可能にしながら:

  • クライアント - [...]
  • サーバー - 保存された状態を要求の間にサーバーに保存します。 の保存済み状態を別のコンテナインスタンスにフェイルオーバーすることを可能にする実装では、サーバ の状態保存戦略を実装する際にこれを覚えておく必要があります。デフォルト実装クライアントモードとサーバモードの両方でビューを直列化します。 サーバーモードでは、このシリアル化されたビューがセッションに格納され、ビューを取得する一意のキーが クライアントに送信されます。シリアル化されたビューをセッションに格納することにより、 コンテナによって提供される通常のメカニズムを使用してフェイルオーバーが発生する可能性があります。言い換える

、AJAXサポート(JSF 1.2 RichFacesの3により添加一つであり、JSF 2.0に組み込まれた1つの両方)JSFに追加のネットワーク帯域幅の消費量ではなく、サーバ側のCPU消費量を低減することを目的とします。

+0

Meritonはあなたの入力に感謝しますが、私は混乱しています。 Ajaxの全体のポイントは、本当に速く、場面の裏で、部分的に再レン​​ダリングすることができると考えられています。私はJSF/Facelets/Richfacesがビューを保存/キャッシュしていると思っていました。もし可能であれば、ビルドされたコンポーネントツリーを再利用します。上記の "復元"と言えば、私たちはキャッシュからの復元や再構築を行う必要があると思います。私は主に、RichFacesタグを使って、このアクションで更新されるページのごく一部だけを必要とするという情報をすべて指定したことに気づきました。なぜ、ツリー全体を構築するのでしょうか? –

+0

私は自分の質問に答えるために私の答えを広げました。 – meriton

+0

あなたのフォローアップのためにメリトンをもう一度おねがいします。私たちの唯一の選択肢は、これらのダイナミックなビューを構築し、設計によって分割するロジックのパフォーマンスを調整することです。これはJSF/Faceletsの設計の観点からは非常に残念ですが、必要でない場合は非常に効率が悪く、わかりません。 –

1

私の分析から、問題はfaceletsの実装によって引き起こされています。ツリーの問題を解決するために

 // build view - but not if we're in "buildBeforeRestore" 
     // land and we've already got a populated view. Note 
     // that this optimizations breaks if there's a "c:if" in 
     // the page that toggles as a result of request processing - 
     // should that be handled? Or 
     // is this optimization simply so minor that it should just 
     // be trimmed altogether? 
     if (!this.buildBeforeRestore 
       || viewToRender.getChildren().isEmpty()) { 
      this.buildView(context, viewToRender); 
     } 

だから私の心の中で:FaceletViewHandlerクラスの次の行は、デバッガに基づいて、それぞれのツリーの(でもAJAX)を再構築する原因となる要求(buildBeforeRestoreはそうbuildViewメソッドが呼び出され、偽です)各リクエストの再構築は、Faceletsの実装に深く関わって、再実装を行うことです...私は、ビューを再構成し、コンポーネントの数を最小限に抑えることを望んでいるので、ツリー時間を短くします。

関連する問題