File APIs for Java Developers
Manipulate DOC, XLS, PPT, PDF and many others from your application.
http://aspose.com/file-tools
The moose likes JSF and the fly likes JSF partial validation Big Moose Saloon
  Search | Java FAQ | Recent Topics | Flagged Topics | Hot Topics | Zero Replies
Register / Login


JavaRanch » Java Forums » Java » JSF
Bookmark "JSF partial validation" Watch "JSF partial validation" New topic
Author

JSF partial validation

Mauro Castaldo
Greenhorn

Joined: Jul 18, 2005
Posts: 22
Looking at many posts about use of immediate attribute it seems that JSF implementation to bypass Process Validations and Update Model Values phases isn't so intuitive and flexible.
Why does you need to choose to validate all UIInput components on one form or to validate none at all?
the immedaite attribute for UICommand component is really useful only in case you need to bypass all validations and updates on the form like cancel buttons, but if you need to validate only fiew UIInput components on the form you need to use immediate="true" and use manual validation and backing bean update using values returned from myInput.getSubmittedValue() property!
Why doesn't JSF use "partial" validation & update like Microsoft does for ASP.NET 2.0 using validationGroup property?
Also Oracle ADF Faces component set implement a subform tag to bypass validation & update in a more flexible way but their solution have a layout constraint. Infact it force validation of a set of components that can be nested into a single subform tag.
I have implemented an approach similar to Microsoft ASP.NET 2.0 (with no layout constraint) using a custom HtmlCommandButton component with validationList attribute and a custom HtmlForm component.
The validationList attribute of the HtmlCommandButton is a comma separated list of UIInput id you want to process during Process Validations and Update Model Values phases.
The decode() method of the HtmlCommandButton put this list into requestMap under a predefined key.
The custom form component is a standard form like HtmlForm of the reference implementation (you can also inherit from HtmlForm) but customize (or override) processValidators(FacesContext context) and processUpdates(FacesContext context) methods to recursively call the same methods only for childen wich have id present in the validation list. These are the custom form methods:




validationListAttribute is the string comma separated list of components id to validate.

Any comment to this solution is appreciated.

Mauro.
Gregg Bolinger
GenRocket Founder
Ranch Hand

Joined: Jul 11, 2001
Posts: 15299
    
    6

I am not clear on why you state that you have to validate all fields or none at all. I have several forms with dozens of fields on each form. Some are validated on submit, some are not and all with the standard validation components. Can you clarify what you mean?


GenRocket - Experts at Building Test Data
Mauro Castaldo
Greenhorn

Joined: Jul 18, 2005
Posts: 22
Originally posted by Gregg Bolinger:
I am not clear on why you state that you have to validate all fields or none at all. I have several forms with dozens of fields on each form. Some are validated on submit, some are not and all with the standard validation components. Can you clarify what you mean?


I'll try to explain what I mean for "validate all fields or none at all".
Imagine you have a web application with a simple page with a simple input form;
in this form you have some UIInput components to take user input, value bounded to a backing-bean;
some of these components are required and each component may or may not use a converter and one or more validators.
On this form you have one UICommand component (for example a commandButton or commandLink) to save the form and one other to cancel and navigate to another page.
In such a simple, monolithic form, with very limited user interaction, you could feel good with JSF simple approach to convertion/validation an model update. Infact, you can use a commandButton with immediate="false" for the save button and a commandButton with immediate="true" for the cancel button.
But imagine you need a more sophisticated user interaction during form input; for example, you may have two or more UISelectOne component that dynamically submit the form to enable or render other components or to update other components state (for example to fill other UISelectOne components).
You certanly need to use some sort of "immediate" and getSubmittedValue() trick to read values from the interactive portion of the page the user is editing because you don't want to trigger other components convertion and/or validation errors and you may need to manually convert and/or validate these components values you want to read. Moreover, if you decide to use immediate="true" / onchange="this.form.submit()" / valueChangeListener combination on more than one component (for example on two UISelectOne) and these components are required (and initially blank) you cannot change the value of one these without throwing a validation error on the other one.
All these problems derives from the impossibility of selecting components to apply process validations and process updates lifecycle phases during a form submit. This can be obtained using a commandButton with a validationList attribute (and, of course, with a javascript version of this somple mechanism in the case of javascript form submission) as reported in my previous example.
Gregg Bolinger
GenRocket Founder
Ranch Hand

Joined: Jul 11, 2001
Posts: 15299
    
    6

So in the value changed listener method for the dropdown lists, just call renderResponse() from the FacesContext object and validation and conversion is bypassed and you can still do what you want. I think you are making the issue more complicated than what it is?
Mauro Castaldo
Greenhorn

Joined: Jul 18, 2005
Posts: 22
Originally posted by Gregg Bolinger:
So in the value changed listener method for the dropdown lists, just call renderResponse() from the FacesContext object and validation and conversion is bypassed and you can still do what you want. I think you are making the issue more complicated than what it is?


obviously you have to call renderResponse() at the end of the valueChangeListener of the two UISelectOne but this don't change the behavior descripted. Infact if you have such situation



changing one of the selectOneMenu you can bypass conversion, validation and update of inputText fields (for example you have no required message from "name" field) but you can't bypass the other selectOneMenu convertion and validation because all convertion and validation of immediate UIInput components are executed during appply request values phase (responseComplete() is evaluated at the end of each phase to bypass next phase but current phase must be completed). You can avoid immediate="true" on the two selectoneMenu and use an hidden UICommand with immediate="true" and an action or actionListener, calling "this.form['myform:mybutton'].click()" instead of this.form.submit() in the two selectOneMenu but you need manual convertion/validation/update of values obtained from getSubmittedValue(). if your item values aren't simple String, for example java.util.Date objects, and you use a DateTimeConverter it would be convenient to use it.
Did you wonder why Oracle propose a subform component in ADF faces?
You can solve all this problems with Orcle subform and (probably better) with the simple solution I posted.

Mauro.
Jorge Fiallega
Greenhorn

Joined: May 27, 2005
Posts: 12
I totally agree with your explanation of the problem and the fact that for somehow a little more complex user interfaces we need the functionality that you describe. It would be nice if you would provide all the working code, so that it can be tested and used

thanks

Jorge Luis
Sergio W. Del Valle
Greenhorn

Joined: Feb 13, 2006
Posts: 3
Maybe you should take a look at the How to Use Virtual Forms tutorial in the SDN.
Jorge Fiallega
Greenhorn

Joined: May 27, 2005
Posts: 12
Thanks, I will look into it.
 
GeeCON Prague 2014
 
subject: JSF partial validation