111
  1. JSFはどの時点までUIコンポーネントの状態をサーバー側に保存し、UIコンポーネントの状態情報がサーバーメモリから削除されるのはいつですか? アプリケーションにログインしたユーザーがページをナビゲートすると、コンポーネントの状態がサーバーに蓄積され続けますか?

  2. サーバー上で UI コンポーネントの状態を保持する利点がわかりません!? 検証/変換されたデータをマネージド Bean に直接渡すだけでは十分ではありませんか? 私はそれを避けることができますか、または避けるべきですか?

  3. 何千もの同時ユーザー セッションがある場合、サーバー側で大量のメモリ消費しませんか? ユーザーが特定のトピックに関するブログを投稿できるアプリケーションがあります。このブログのサイズはかなり大きいです。ポストバックやブログ閲覧のリクエストがあった場合、この大きなページのデータはコンポーネントの状態の一部として保存されますか? これはあまりにも多くのメモリを消費します。これは気になりませんか?


更新 1:

現在、JSF の使用中に状態を保存する必要はありません。高パフォーマンスのステートレス JSF 実装が利用可能です。関連する詳細と議論については、このブログこの質問を参照してください。また、 JSF にステートレス モードを提供するオプションである JSF 仕様に含める未解決の問題があります。(PSが便利な機能である場合は、これこれの問題に投票することを検討してください。)


更新 2 (2013 年 2 月 24 日):

Mojarra 2.1.19ステートレス モードでリリースされたという素晴らしいニュースです。

ここを参照してください:

http://weblogs.java.net/blog/mriem/archive/2013/02/08/jsf-going-stateless?force=255

http://java.net/jira/browse/JAVASERVERFACES-2731

http://balusc.blogspot.de/2013/02/stateless-jsf.html

4

1 に答える 1

204

JSF がサーバー側の UI コンポーネントの状態を保存する必要があるのはなぜですか?

HTTP はステートレスで、JSF はステートフルだからです。JSF コンポーネント ツリーは、動的 (プログラムによる) 変更の影響を受けます。JSF は、フォームがエンドユーザーに表示されたときの正確な状態を知る必要があるだけです。これにより、フォームがエンドユーザーに送信されたときに、元の JSF コンポーネント ツリーによって提供される情報に基づいて、JSF ライフサイクル全体を正常に処理できます。サーバー。コンポーネント ツリーは、要求パラメーター名、必要なコンバーター/バリデーター、バインドされたマネージド Bean のプロパティ、およびアクション メソッドに関する情報を提供します。


JSF はどの時点まで UI コンポーネントの状態をサーバー側に保存しますか?また、UI コンポーネントの状態情報がサーバーのメモリから削除されるのは正確にはいつですか?

これらの 2 つの質問は、要約すると同じように思えます。とにかく、これは実装固有であり、状態がサーバーまたはクライアントに保存されるかどうかにも依存します。少しまともな実装では、有効期限が切れたとき、またはキューがいっぱいになったときに削除されます。たとえば、状態の保存がセッションに設定されている場合、Mojarra にはデフォルトで 15 の論理ビューの制限があります。これは、次のコンテキスト パラメータを使用して設定できますweb.xml

<context-param>
    <param-name>com.sun.faces.numberOfLogicalViews</param-name>
    <param-value>15</param-value>
</context-param>

他の Mojarra 固有のパラメーターについてはMojarra FAQも参照してください。また、この関連する回答com.sun.faces.numberOfViewsInSession vs com.sun.faces.numberOfLogicalViewsも参照してください。


アプリケーションにログインしたユーザーがページをナビゲートすると、コンポーネントの状態がサーバーに蓄積され続けますか?

技術的には、それは実装に依存します。ページ間のナビゲーション (GET リクエストのみ) について話している場合、Mojarra はセッションに何も保存しません。ただし、それらが POST リクエスト (コマンドリンク/ボタンを含むフォーム) である場合、Mojarra は最大制限までセッション内の各フォームの状態を保存します。これにより、エンドユーザーは同じセッション内の異なるブラウザー タブで複数のフォームを開くことができます。

または、状態保存がクライアントに設定されている場合、JSF はセッションに何も保存しません。の次のコンテキスト パラメータでそれを行うことができますweb.xml

<context-param>
    <param-name>javax.faces.STATE_SAVING_METHOD</param-name>
    <param-value>client</param-value>
</context-param>

javax.faces.ViewState次に、フォームの名前を持つ非表示の入力フィールドで、暗号化された文字列にシリアル化されます。


サーバー側で UI コンポーネントの状態を保持することの利点がわかりません。検証/変換されたデータをマネージド Bean に直接渡すだけでは十分ではありませんか? 私はそれを避けることができますか/すべきですか?

JSF の整合性と堅牢性を確保するには、それだけでは不十分です。JSF は、単一の制御エントリー・ポイントを持つ動的フレームワークです。状態管理がなければ、HTTP リクエストを特定の方法でスプーフィング/ハッキングして (たとえばdisabledreadonlyrendered属性を操作するなど)、JSF にさまざまな (そして潜在的に危険な) ことをさせることができます。CSRF 攻撃やフィッシングの被害を受ける可能性さえあります。


また、何千もの同時ユーザー セッションがある場合、サーバー側で大量のメモリを消費しませんか? ユーザーが特定のトピックに関するブログを投稿できるアプリケーションがあります。このブログのサイズはかなり大きいです。ポストバックまたはブログの閲覧要求がある場合、大規模なブログはコンポーネントの状態の一部として保存されます。これは大量のメモリを消費します。これは気になりませんか?

メモリは特に安価です。アプリケーションサーバーに十分なメモリを与えるだけです。または、ネットワーク帯域幅の方が安い場合は、状態保存をクライアント側に切り替えるだけです。最適な一致を見つけるには、予想される同時ユーザーの最大数を使用して webapp のストレステストとプロファイリングを行い、appserver に測定された最大メモリの 125% ~ 150% を与えます。

JSF 2.0 では状態管理が大幅に改善されていることに注意してください。部分的な状態を保存することもできます (たとえば、最後までの全体ではなく、のみ保存されます)。たとえば、モハラはそれを行います。10 個の入力フィールド (それぞれにラベルとメッセージがあります) と 2 つのボタンを含む平均的なフォームは、1KB しかかかりません。セッションに 15 個のビューがある場合、セッションごとに 15KB を超えないようにする必要があります。最大 1000 の同時ユーザー セッションでは、15MB を超えないようにする必要があります。<h:form><html>

あなたの懸念は、セッションまたはアプリケーションスコープ内の実際のオブジェクト (マネージド Bean および/または DB エンティティ) にもっと集中する必要があります。SQL の代わりに Java を使用してレコードをフィルタリング/グループ化/配置するセッション スコープ Bean のフレーバーで、データベース テーブル全体を Java のメモリに不必要に複製する多くのコードとプロジェクトを見てきました。最大 1000 レコードの場合、ユーザー セッションごとに 10 MB を簡単に超えてしまいます。

于 2011-03-29T16:09:20.613 に答える