validation - JSF2 disabled attribute for validator evaluated only for first cycle? -
validation - JSF2 disabled attribute for validator evaluated only for first cycle? -
i found disabled attribute validator utilize in jsf2 evaluated in first cycle if managed bean viewscoped.
but create utilize of disabled attribute validators based on info 4th update phase. expect reevaluated in cycles performed on same view.
example xhtml page:
<!doctype html public "-//w3c//dtd xhtml 1.0 transitional//en" "http://www.w3.org/tr/xhtml1/dtd/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml" xmlns:h="http://java.sun.com/jsf/html" xmlns:f="http://java.sun.com/jsf/core"> <h:head></h:head> <h:body> <h:form> <h:panelgrid id="pnlgrid"> <h:inputtext id="somevalueid" value="#{testpagebean.somevalue}"> <f:validatelength minimum="2" maximum="4" disabled="#{testpagebean.disablevalidatelength}"/> </h:inputtext> <h:messages for="somevalueid"/> <h:commandbutton action="#{testpagebean.dosomething}" value="do something" /> </h:panelgrid> </h:form> </h:body> </html>
and view scoped managed bean
package cz.kamosh; import java.io.serializable; import javax.faces.bean.managedbean; import javax.faces.bean.viewscoped; @managedbean @viewscoped public class testpagebean implements serializable { boolean disablevalidatelength = false; private string somevalue; public testpagebean() { system.out.println("constructor testpagebean"); } public string getsomevalue() { homecoming somevalue; } public void setsomevalue(string somevalue) { this.somevalue = somevalue; } /** * action without navigation result */ public void dosomething() { disablevalidatelength = !disablevalidatelength; system.out.printf( "dosomething, somevalue: %1$s, disablevalidatelength: %2$b\n", somevalue, disablevalidatelength); } public boolean isdisablevalidatelength() { system.out.printf("isvalidatelength, disablevalidatelength: %1$b\n", disablevalidatelength); homecoming disablevalidatelength; } }
i know should blame implementation com.sun.faces.facelets.tag.jsf.validatortaghandlerdelegateimpl:
private void applynested(faceletcontext ctx, uicomponent parent) { // process if it's been created if (!componenthandler.isnew(parent)) { return; } ... }
these 3 rows cause validator not beingness reevaluated disabled attribute when perform action:-(
could please give me hint, motivation jsf2 guys implement way or improve how solve problem?
edit:
version of jsf2: 2.0.3-snapshot
web.xml:
<?xml version="1.0" encoding="utf-8"?> <web-app xmlns:xsi="http://www.w3.org/2001/xmlschema-instance" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" xsi:schemalocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" id="webapp_id" version="2.5"> <display-name>jsf2testing</display-name> <servlet> <servlet-name>faces servlet</servlet-name> <servlet-class>javax.faces.webapp.facesservlet</servlet-class> <load-on-startup>1</load-on-startup> </servlet> <servlet-mapping> <servlet-name>faces servlet</servlet-name> <url-pattern>/faces/*</url-pattern> </servlet-mapping> <context-param> <param-name>javax.faces.partial_state_saving</param-name> <param-value>false</param-value> </context-param> </web-app>
edit2 effort follow balusc' suggestion
changes on page:
<h:inputtext id="somevalueid" value="#{testpagebean.somevalue}"> <f:validator validatorid="mylengthvalidator"/> <f:attribute name="disablemylengthvalidator" value="#{testpagebean.disablevalidatelength}"/> <f:attribute name="minimum" value="2" /> <f:attribute name="maximum" value="4" /> </h:inputtext>
own validator used instead of standard :
import java.io.serializable; import javax.faces.component.uicomponent; import javax.faces.context.facescontext; import javax.faces.validator.facesvalidator; import javax.faces.validator.lengthvalidator; import javax.faces.validator.validatorexception; @facesvalidator("mylengthvalidator") public class mylengthvalidator extends lengthvalidator implements serializable { public mylengthvalidator() { system.out.println("mylengthvalidator constructor"); } @override public void validate(facescontext context, uicomponent component, object value) throws validatorexception { if((boolean)component.getattributes().get("disablemylengthvalidator")) { return; } setminimum(integer.valueof((string)component.getattributes().get("minimum"))); setmaximum(integer.valueof((string)component.getattributes().get("maximum"))); super.validate(context, component, value); } }
my notes solution:
requires own implementation if standard validators is dependent on attributes on component (inputtext) level validator triggered if should not be i pretty sure not behave expect when client side validation provided validator i consider ugly , not next jsf2 :-(
you've become victim of chicken-egg issue partial state saving , view scoped beans described in issue 1492 fixed in upcoming mojarra 2.2.
you should have realized something's not exclusively right when saw constructor of view scoped bean beingness invoked on every request instead of 1 time @ first request of view.
one of ways prepare disable partial state saving altogether:
<context-param> <param-name>javax.faces.partial_state_saving</param-name> <param-value>false</param-value> </context-param>
see also: communication in jsf 2 - @viewscoped
fails in tag handlers why f:validatedoublerange work @sessionscoped? validation jsf-2
Comments
Post a Comment