更新用のアクションは実行されますが、画面で入力した値がDTOのフィールドにセットされていません。
いろいろと試してみると、s:forEachとm:renderedの属性値に使うリストをte:inputHiddenで持っていることが原因のようです。試しにセッションに入れてみると、無事に更新されます。
そこを足掛りに調べてみれば、Teeda ExtensionのinputHiddenの仕様「Validationフェーズを正常終了すると、すぐにModelを更新する」にたどりつきました。
JSFでのリクエスト処理のライフサイクルは、
te:inputHiddenで画面に持たせたリストは、仕様によれば3の「Process Validation」で復元されます。ところが画面で入力した値を扱うのは2の「Apply Request Values」です。この「Apply Request Values」でそのリストを使いたいのです。
そこで「m:immediate=true」ならば「Apply Request Values」のときに復元するように変更してみました。
目論見通りにte:inputHiddenだけで更新されています。これでセッションオブジェクトを大きくしてしまう罪悪感から逃れられそうです。
Teeda 1.0.13-rc4で試してみました。
JSFでのリクエスト処理のライフサイクルは、
- Restore View
- Apply Request Values
- Process Validation
- Update Model Values
- Invoke Application
- Render Response
te:inputHiddenで画面に持たせたリストは、仕様によれば3の「Process Validation」で復元されます。ところが画面で入力した値を扱うのは2の「Apply Request Values」です。この「Apply Request Values」でそのリストを使いたいのです。
そこで「m:immediate=true」ならば「Apply Request Values」のときに復元するように変更してみました。
--- javax/faces/component/html/HtmlInputHidden.java.orig
+++ javax/faces/component/html/HtmlInputHidden.java
@@ -45,12 +45,6 @@
if (!isImmediate()) {
executeValidate(context);
}
- try {
- updateModelImmediately(context);
- } catch (RuntimeException e) {
- context.renderResponse();
- throw e;
- }
}
protected void updateModelImmediately(FacesContext context) {
@@ -73,4 +67,15 @@
setValid(false);
}
}
-}
+
+ public void validate(FacesContext context) {
+ super.validate(context);
+ try {
+ updateModelImmediately(context);
+ } catch (RuntimeException e) {
+ context.renderResponse();
+ throw e;
+ }
+ }
+
+}
目論見通りにte:inputHiddenだけで更新されています。これでセッションオブジェクトを大きくしてしまう罪悪感から逃れられそうです。
Teeda 1.0.13-rc4で試してみました。
0 件のコメント:
コメントを投稿