の実行順序と回数に問題がありf:event type="preRenderView"
ます。
ここでの検索中に、BalusC からの通常の回答として、これと私の問題に関連するこの投稿を見つけましたが、それでも私には 2 つの質問が残っています。
f:event type="preRenderView"
テンプレート ファイル (すべてのビューに適用されるユーザー状態のチェックなどの一般的なタスクを管理するため) に 1 つを配置し、各ビュー (ビュー固有の初期化を処理するため) に別のファイルを配置するとf:event type="preRenderView"
、なぜビューからリスナー メソッドが呼び出されるのか疑問に思います。テンプレートからのものの前に。提案どおりに全体を配置する
<f:metadata><f:event [..] /></f:metadata>
とui:define
、ログインページからそのページにリダイレクトした後に2回呼び出されますが、1回だけ呼び出された後、1レベル上に配置するui:composition
と。
更新: 例
次の例は、上記の動作を示しています。
これは、すべてのビューのハンドラーで共通メソッドを呼び出すイベントtemplate_test.xhtml
のリスナーを含むテンプレート ファイルです。preRenderView
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xml:lang="de" lang="de" xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:ui="http://java.sun.com/jsf/facelets">
<h:head>
<link rel="stylesheet" type="text/css" href="../resources/css/style.css" />
</h:head>
<h:body>
<f:event type="preRenderView" listener="#{testHandler.initCommon()}" />
<div id="content">
<ui:insert name="content" />
</div>
</h:body>
</html>
これはビュー ファイルで、ハンドラーでビュー固有のメソッドを呼び出すイベントtest.xhtml
のリスナーpreRenderView
と、ハンドラー メソッドを介してリダイレクトするコマンド ボタンも含まれています。
<?xml version="1.0" encoding="UTF-8"?>
<ui:composition xmlns="http://www.w3.org/1999/xhtml"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:ui="http://java.sun.com/jsf/facelets"
template="template_test.xhtml">
<ui:define name="content">
<f:metadata>
<f:event type="preRenderView"
listener="#{testHandler.initIndividual()}"></f:event>
</f:metadata>
<h:form>
<h:commandButton value="Redirect" action="#{testHandler.redirect()}" />
</h:form>
</ui:define>
</ui:composition>
TestHandler.java
これは、3 つのメソッドを含むハンドラ クラスです。
package test;
import java.io.Serializable;
import javax.enterprise.context.SessionScoped;
import javax.inject.Named;
@Named
@SessionScoped
public class TestHandler implements Serializable {
private static final long serialVersionUID = -2785693292020668741L;
public void initCommon() {
System.out.println("Common init called.");
}
public void initIndividual() {
System.out.println("Init for individual page called.");
}
public String redirect() {
return "test/test.xhtml?faces-redirect=true";
}
}
テストページをリクエストすると、Tomcat ログに次のように表示されます。
Init for individual page called.
Common init called.
Init for individual page called.
これはノーを示しています。1、ビューからのイベントハンドラーがテンプレートからのイベントハンドラーの前に呼び出され、いいえ。2、ビューからのイベント ハンドラーが 2 回呼び出されること。
また、ページがリダイレクトによって要求された場合に何が起こるかを示す 3 番目のポイント (同じページへのリダイレクトを含むボタンを含めた理由) も示しています。個々のページはさらに何度も呼び出されます。
Init for individual page called.
Common init called.
Init for individual page called.
Init for individual page called.
どちらもいいえ。2 と 3 は、メタデータ セクション全体を の上に置くかui:define
、URL に含まれていないビューのメタデータ セクションにダミー パラメータを追加することで回避できます。
<f:metadata>
<f:viewParam name="dummyToDenySecondRedirect" />
<f:event type="preRenderView"
listener="#{testHandler.initIndividual()}"></f:event>
</f:metadata>
誰かがこれらのケースの理由を教えてもらえますか?