You are viewing a plain text version of this content. The canonical link for it is here.
Posted to users@myfaces.apache.org by Jesus Jr M Salvo <je...@gmail.com> on 2012/11/13 10:17:49 UTC
Extval: Getting a simple @RequiredIf working in JSF2
Hi,
As can be seen from the subject, I haven't used Extval before, and I
am having trouble testing out a simple proof-of-concept for
cross-validation in a JSF2 application.
My environment is as follows:
1) JBoss 7.1.1 ( NOT using MyFaces Core, but using the built-in
Mojarra JSF implementation )
2) Extval JARs in WEB-INF/lib:
myfaces-extval-bean-validation-2.0.5.jar
myfaces-extval-core-2.0.5.jar
myfaces-extval-property-validation-2.0.5.jar
I did not include myfaces-extval-generic-support-2.0.5.jar as I get a
Caused by: java.lang.ClassNotFoundException:
net.sf.cglib.proxy.MethodInterceptor
I could not find what version of cglib and asm is required, so I
downloaded the latest versions of cglib and asm from the corresponding
websites and added them to WEB-INF/lib. But then, I get:
java.lang.VerifyError: class net.sf.cglib.core.DebuggingClassWriter
overrides final method visit
Critical error during deployment: : java.lang.NoClassDefFoundError:
net/sf/cglib/core/DebuggingClassWriter
So therefore removed myfaces-extval-generic-support-2.0.5.jar. It
seems that I don't really need it anyway. After removing
generic-support, JBoss startsup.
But anyway, back to the original question, I need to conditionally
validate that a property is required only when another property is set
to a specific value. So, I have the following bean:
package test;
import java.io.Serializable;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.ViewScoped;
import org.apache.myfaces.extensions.validator.crossval.annotation.RequiredIf;
@ManagedBean
@ViewScoped
public class ViewBean implements Serializable {
private static final long serialVersionUID = 1L;
private String type;
@RequiredIf(valueOf="#{type eq 'OPT2'}")
private String text;
public String getType() {
return type;
}
public String getText() {
return text;
}
public void setType(String type) {
this.type = type;
}
public void setText(String text) {
this.text = text;
}
}
In the bean above, I only want to indicate that the property "text" is
required only if the property type is "OPT2". The sample XHTML file
below shows a fixed list of f:selectItems, one of which has a
itemValue of "OPT2", which I am expecting that, if I select the option
of "OPT2" ( with label of "Option 2" ), and I leave the text field
blank ( thereby leaving the "text" property of the bean empty, I am
expecting an output from h:messages.
<!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"
xmlns:ui="http://java.sun.com/jsf/facelets">
<h:head></h:head>
<body>
<h:form>
Type:<h:selectOneMenu id="f_clmTyp" value="#{viewBean.type}"
required="true" requiredMessage="Claim Type is required">
<f:selectItem itemLabel="Option 1" itemValue="OPT1"/>
<f:selectItem itemLabel="Option 2" itemValue="OPT2"/>
<f:selectItem itemLabel="Option 3" itemValue="OPT3"/>
</h:selectOneMenu>
<br/>
Text:
<h:inputText id="f_text" value="#{viewBean.text}"/>
<br/>
<h:commandButton name="Submit" value="Submit"/>
<br/>
</h:form>
Submitted type: <h:outputText value="#{viewBean.type}"/><br/>
Submitted text: <h:outputText value="#{viewBean.text}"/>
<h:messages/>
</body>
</html>
In WEB-INF/web.xml, I have:
<context-param>
<param-name>javax.faces.INTERPRET_EMPTY_STRING_SUBMITTED_VALUES_AS_NULL</param-name>
<param-value>false</param-value>
</context-param>
<context-param>
<param-name>javax.faces.STATE_SAVING_METHOD</param-name>
<param-value>client</param-value>
</context-param>
But when I submit the form, I do not get any validation messages
outputted by h:messages.
I must be missing something simple, but what is it ??
Note: I have also tried setting
javax.faces.INTERPRET_EMPTY_STRING_SUBMITTED_VALUES_AS_NULL to true
with the same result. In any case, in the long run, I have to rely on
setting it to false because of existing bugs in both Mojarra and
MyFaces core implementations ( actually, in the JSF specs themslves )
with regards to this context parameter:
https://forums.oracle.com/forums/thread.jspa?threadID=2459557&tstart=0
https://issues.apache.org/jira/browse/MYFACES-3525
http://java.net/jira/browse/JAVASERVERFACES-2262
http://java.net/jira/browse/JAVASERVERFACES_SPEC_PUBLIC-939
Also, another question is .. and maybe answers my original question
above.. how does Extval perform cross-validation on the bean
properties when according to the JSF lifecycle, the bean properties
are updated ( UPDATE_MODEL_VALUES ) AFTER the validation phase (
PROCESS_VALIDATION ) ?
Thanks,
John
Re: Extval: Getting a simple @RequiredIf working in JSF2
Posted by Gerhard Petracek <ge...@gmail.com>.
hi john,
@ #1:
in case of el-expressions extval records the ValueExpression of the
EditableValueHolder components during the validation phase and stores them
side by side with the converted value,... . -> you can use those
expressions to reference a target. if your validation target isn't a
value-binding or it doesn't get submitted with the same request, extval
just delegates to the jsf-api
(javax.faces.application.Application#evaluateExpressionGet) for resolving
the value.
-> it looks like you are just trying something which isn't supported
out-of-the-box. however, (if needed) you can register your
own ReferencingStrategy which allows to implement your own concepts for
resolving the target-value.
@ #2:
it's done at the end of the validation phase of jsf (see e.g. [1] - slide
28)
@ #3:
please start a new thread about myfaces-core and
javax.faces.INTERPRET_EMPTY_STRING_SUBMITTED_VALUES_AS_NULL
(extval supports this config-parameter as well, but with 'true' as the
default value.)
regards,
gerhard
[1]
http://os890.blogspot.co.at/2009/12/metadata-based-validation-ejug-seminar.html
http://www.irian.at
Your JSF/JavaEE powerhouse -
JavaEE Consulting, Development and
Courses in English and German
Professional Support for Apache MyFaces
2012/11/13 Jesus Jr M Salvo <je...@gmail.com>
> Hi,
>
> As can be seen from the subject, I haven't used Extval before, and I
> am having trouble testing out a simple proof-of-concept for
> cross-validation in a JSF2 application.
>
> My environment is as follows:
>
> 1) JBoss 7.1.1 ( NOT using MyFaces Core, but using the built-in
> Mojarra JSF implementation )
> 2) Extval JARs in WEB-INF/lib:
>
> myfaces-extval-bean-validation-2.0.5.jar
> myfaces-extval-core-2.0.5.jar
> myfaces-extval-property-validation-2.0.5.jar
>
> I did not include myfaces-extval-generic-support-2.0.5.jar as I get a
>
> Caused by: java.lang.ClassNotFoundException:
> net.sf.cglib.proxy.MethodInterceptor
>
> I could not find what version of cglib and asm is required, so I
> downloaded the latest versions of cglib and asm from the corresponding
> websites and added them to WEB-INF/lib. But then, I get:
>
> java.lang.VerifyError: class net.sf.cglib.core.DebuggingClassWriter
> overrides final method visit
> Critical error during deployment: : java.lang.NoClassDefFoundError:
> net/sf/cglib/core/DebuggingClassWriter
>
> So therefore removed myfaces-extval-generic-support-2.0.5.jar. It
> seems that I don't really need it anyway. After removing
> generic-support, JBoss startsup.
>
> But anyway, back to the original question, I need to conditionally
> validate that a property is required only when another property is set
> to a specific value. So, I have the following bean:
>
> package test;
>
> import java.io.Serializable;
>
> import javax.faces.bean.ManagedBean;
> import javax.faces.bean.ViewScoped;
>
> import
> org.apache.myfaces.extensions.validator.crossval.annotation.RequiredIf;
>
> @ManagedBean
> @ViewScoped
> public class ViewBean implements Serializable {
>
> private static final long serialVersionUID = 1L;
>
> private String type;
> @RequiredIf(valueOf="#{type eq 'OPT2'}")
> private String text;
>
> public String getType() {
> return type;
> }
>
> public String getText() {
> return text;
> }
>
> public void setType(String type) {
> this.type = type;
> }
>
> public void setText(String text) {
> this.text = text;
> }
>
> }
>
> In the bean above, I only want to indicate that the property "text" is
> required only if the property type is "OPT2". The sample XHTML file
> below shows a fixed list of f:selectItems, one of which has a
> itemValue of "OPT2", which I am expecting that, if I select the option
> of "OPT2" ( with label of "Option 2" ), and I leave the text field
> blank ( thereby leaving the "text" property of the bean empty, I am
> expecting an output from h:messages.
>
>
> <!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"
> xmlns:ui="http://java.sun.com/jsf/facelets">
>
> <h:head></h:head>
> <body>
> <h:form>
> Type:<h:selectOneMenu id="f_clmTyp"
> value="#{viewBean.type}"
> required="true" requiredMessage="Claim Type is
> required">
> <f:selectItem itemLabel="Option 1" itemValue="OPT1"/>
> <f:selectItem itemLabel="Option 2" itemValue="OPT2"/>
> <f:selectItem itemLabel="Option 3" itemValue="OPT3"/>
> </h:selectOneMenu>
> <br/>
> Text:
> <h:inputText id="f_text" value="#{viewBean.text}"/>
> <br/>
> <h:commandButton name="Submit" value="Submit"/>
> <br/>
> </h:form>
> Submitted type: <h:outputText value="#{viewBean.type}"/><br/>
> Submitted text: <h:outputText value="#{viewBean.text}"/>
> <h:messages/>
> </body>
> </html>
>
>
> In WEB-INF/web.xml, I have:
>
> <context-param>
>
> <param-name>javax.faces.INTERPRET_EMPTY_STRING_SUBMITTED_VALUES_AS_NULL</param-name>
> <param-value>false</param-value>
> </context-param>
> <context-param>
> <param-name>javax.faces.STATE_SAVING_METHOD</param-name>
> <param-value>client</param-value>
> </context-param>
>
> But when I submit the form, I do not get any validation messages
> outputted by h:messages.
> I must be missing something simple, but what is it ??
>
> Note: I have also tried setting
> javax.faces.INTERPRET_EMPTY_STRING_SUBMITTED_VALUES_AS_NULL to true
> with the same result. In any case, in the long run, I have to rely on
> setting it to false because of existing bugs in both Mojarra and
> MyFaces core implementations ( actually, in the JSF specs themslves )
> with regards to this context parameter:
>
> https://forums.oracle.com/forums/thread.jspa?threadID=2459557&tstart=0
> https://issues.apache.org/jira/browse/MYFACES-3525
> http://java.net/jira/browse/JAVASERVERFACES-2262
> http://java.net/jira/browse/JAVASERVERFACES_SPEC_PUBLIC-939
>
> Also, another question is .. and maybe answers my original question
> above.. how does Extval perform cross-validation on the bean
> properties when according to the JSF lifecycle, the bean properties
> are updated ( UPDATE_MODEL_VALUES ) AFTER the validation phase (
> PROCESS_VALIDATION ) ?
>
> Thanks,
>
> John
>