myfaces-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From al...@apache.org
Subject svn commit: r983131 - in /myfaces/gsoc/html5-comp-lib/trunk: html5-comp-lib-core/ html5-comp-lib-core/src/main/java/org/apache/myfaces/html5/component/api/validation/ html5-comp-lib-core/src/main/java/org/apache/myfaces/html5/component/input/ html5-com...
Date Fri, 06 Aug 2010 21:35:09 GMT
Author: aliok
Date: Fri Aug  6 21:35:08 2010
New Revision: 983131

URL: http://svn.apache.org/viewvc?rev=983131&view=rev
Log:
Improved client-side validation by driving JSF validators/converters.
Added an example.
Added TODOs

Added:
    myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-core/src/main/java/org/apache/myfaces/html5/component/api/validation/
    myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-core/src/main/java/org/apache/myfaces/html5/component/api/validation/ClientSidePatternProvider.java
Modified:
    myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-core/   (props changed)
    myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-core/src/main/java/org/apache/myfaces/html5/component/input/AbstractHtmlInputText.java
    myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-core/src/main/java/org/apache/myfaces/html5/renderkit/input/util/InputPatternRendererUtil.java
    myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-examples/   (props changed)
    myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-examples/src/main/java/org/apache/myfaces/html5/examples/showcase/beans/InputTextBean.java
    myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-examples/src/main/webapp/inputText/inputText04.xhtml

Propchange: myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-core/
------------------------------------------------------------------------------
--- svn:ignore (added)
+++ svn:ignore Fri Aug  6 21:35:08 2010
@@ -0,0 +1,4 @@
+.settings
+target
+.classpath
+.project

Added: myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-core/src/main/java/org/apache/myfaces/html5/component/api/validation/ClientSidePatternProvider.java
URL: http://svn.apache.org/viewvc/myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-core/src/main/java/org/apache/myfaces/html5/component/api/validation/ClientSidePatternProvider.java?rev=983131&view=auto
==============================================================================
--- myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-core/src/main/java/org/apache/myfaces/html5/component/api/validation/ClientSidePatternProvider.java
(added)
+++ myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-core/src/main/java/org/apache/myfaces/html5/component/api/validation/ClientSidePatternProvider.java
Fri Aug  6 21:35:08 2010
@@ -0,0 +1,14 @@
+package org.apache.myfaces.html5.component.api.validation;
+
+/**
+ * Provides regex pattern to use it on client-side.
+ * <br>
+ * Server-side validation against the pattern is responsibility of implementing JSF validator/converter.
+ * @author Ali Ok
+ *
+ */
+public interface ClientSidePatternProvider
+{
+    public String getPattern();
+
+}

Modified: myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-core/src/main/java/org/apache/myfaces/html5/component/input/AbstractHtmlInputText.java
URL: http://svn.apache.org/viewvc/myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-core/src/main/java/org/apache/myfaces/html5/component/input/AbstractHtmlInputText.java?rev=983131&r1=983130&r2=983131&view=diff
==============================================================================
--- myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-core/src/main/java/org/apache/myfaces/html5/component/input/AbstractHtmlInputText.java
(original)
+++ myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-core/src/main/java/org/apache/myfaces/html5/component/input/AbstractHtmlInputText.java
Fri Aug  6 21:35:08 2010
@@ -48,8 +48,7 @@ public abstract class AbstractHtmlInputT
      * HTML type of the input.
      * <br/>
      * Possible values are "text"(default), "search", "url", "tel", "textarea" and "password".

-     * If this is set to "textarea", "pattern" property should not be set, and even if it
is set, it is ignored.
-     * @see AbstractHtmlInputText#getPattern()
+     * If this is set to "textarea", pattern is ignored.
      * @see AbstractHtmlInputText#getSuggestions()
      * @see AbstractHtmlInputText#getList()
      * @see AbstractHtmlInputText#getCols()

Modified: myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-core/src/main/java/org/apache/myfaces/html5/renderkit/input/util/InputPatternRendererUtil.java
URL: http://svn.apache.org/viewvc/myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-core/src/main/java/org/apache/myfaces/html5/renderkit/input/util/InputPatternRendererUtil.java?rev=983131&r1=983130&r2=983131&view=diff
==============================================================================
--- myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-core/src/main/java/org/apache/myfaces/html5/renderkit/input/util/InputPatternRendererUtil.java
(original)
+++ myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-core/src/main/java/org/apache/myfaces/html5/renderkit/input/util/InputPatternRendererUtil.java
Fri Aug  6 21:35:08 2010
@@ -23,9 +23,16 @@ import java.io.IOException;
 import javax.faces.component.UIInput;
 import javax.faces.context.FacesContext;
 import javax.faces.context.ResponseWriter;
+import javax.faces.convert.Converter;
+import javax.faces.convert.NumberConverter;
+import javax.faces.validator.DoubleRangeValidator;
+import javax.faces.validator.LengthValidator;
+import javax.faces.validator.LongRangeValidator;
 import javax.faces.validator.RegexValidator;
 import javax.faces.validator.Validator;
 
+import org.apache.commons.lang.StringUtils;
+import org.apache.myfaces.html5.component.api.validation.ClientSidePatternProvider;
 import org.apache.myfaces.html5.renderkit.util.HTML5;
 
 /**
@@ -38,28 +45,144 @@ public class InputPatternRendererUtil
 {
 
     /**
-     * Iterates over the validators of the given UIInput and renders the pattern attr if
found one.
+     * Iterates over the validators and converter of the given UIInput and renders the pattern
attr if found one.
      * <p>
-     * If there are multiple RegexValidator instances attached to components, only the pattern
of the first one will be
-     * used.
+     * If there are multiple validator instances attached to component, only the pattern
of the first one will be used.
      * 
-     * @return true if the RegexValidator is found an the pattern markup is written. false
otherwise.
+     * @return true if a pattern is found or calculated and the pattern markup is written.
false otherwise.
      * @throws IOException
      */
     public static boolean renderPattern(FacesContext facesContext, UIInput component) throws
IOException
     {
-        Validator[] validators = component.getValidators();
+        String pattern = null;
+
+        pattern = _getPatternFromValidators(component.getValidators());
+
+        if (pattern == null)
+            pattern = _getPatternFromConverter(component.getConverter());
+
+        if (pattern != null)
+        {
+            ResponseWriter writer = facesContext.getResponseWriter();
+            writer.writeAttribute(HTML5.PATTERN_ATTR, pattern, null);
+            return true;
+        }
+        else
+        {
+            return false;
+        }
+
+    }
+
+    private static String _getPatternFromConverter(Converter converter)
+    {
+        String pattern = null;
+
+        if (converter instanceof ClientSidePatternProvider)
+            pattern = ((ClientSidePatternProvider) converter).getPattern();
+
+        if (StringUtils.isBlank(pattern))
+            pattern = _getPatternFromStandardConverter(pattern, converter);
+
+        return pattern;
+    }
+
+    private static String _getPatternFromStandardConverter(String pattern, Converter converter)
+    {
+        if (converter instanceof NumberConverter) // special case
+        {
+            pattern = _getPatternFromNumberConverter((NumberConverter) converter);
+        }
+        //TODO: what about DateTimeConverter
+        return pattern;
+    }
+
+    private static String _getPatternFromNumberConverter(NumberConverter converter)
+    {
+        //TODO: read the spec and create the pattern!
+        return null;
+    }
+
+    private static String _getPatternFromValidators(Validator[] validators)
+    {
+        String pattern = null;
+
         for (Validator validator : validators)
         {
-            if (validator instanceof RegexValidator)
+            if (validator instanceof ClientSidePatternProvider)
             {
-                RegexValidator regexValidator = (RegexValidator) validator;
-                String pattern = regexValidator.getPattern();
-                ResponseWriter writer = facesContext.getResponseWriter();
-                writer.writeAttribute(HTML5.PATTERN_ATTR, pattern, null);
-                return true;
+                pattern = ((ClientSidePatternProvider) validator).getPattern();
             }
+
+            if (StringUtils.isBlank(pattern))
+                pattern = _getPatternFromStandardValidator(pattern, validator);
+
+            if (!StringUtils.isBlank(pattern))
+                break;
         }
-        return false;
+
+        return pattern;
+    }
+
+    private static String _getPatternFromStandardValidator(String pattern, Validator validator)
+    {
+        if (validator instanceof RegexValidator) // special case
+        {
+            pattern = _getPatternFromRegexValidator((RegexValidator) validator);
+        }
+        else if (validator instanceof LengthValidator) // special case
+        {
+            pattern = _getPatternFromLengthValidator((LengthValidator) validator);
+        }
+        else if (validator instanceof LongRangeValidator) // special case
+        {
+            pattern = _getPatternFromLongRangeValidator((LongRangeValidator) validator);
+        }
+        else if (validator instanceof DoubleRangeValidator) // special case
+        {
+            pattern = _getPatternFromDoubleRangeValidator((DoubleRangeValidator) validator);
+        }
+        //TODO: what about bean validation? f:validateBean
+        
+        //f:validateRequired is not about pattern, so skip it
+        return pattern;
+    }
+
+    private static String _getPatternFromDoubleRangeValidator(DoubleRangeValidator validator)
+    {
+        // XXX: no real solution!
+        return null;
+    }
+
+    private static String _getPatternFromLongRangeValidator(LongRangeValidator validator)
+    {
+        // XXX: no real solution!
+        return null;
+    }
+
+    private static String _getPatternFromLengthValidator(LengthValidator validator)
+    {
+        // XXX: fix this ugly code
+        int minimum = validator.getMinimum();
+        int maximum = validator.getMaximum();
+
+        boolean hasMinimum = minimum != Integer.MIN_VALUE;
+        boolean hasMaximum = maximum != Integer.MAX_VALUE;
+
+        if (hasMinimum && hasMaximum)
+            return "(?:.{" + minimum + "," + maximum + "})";
+
+        if (hasMinimum)
+            return "(?:.{" + minimum + ",})";
+
+        if (hasMaximum)
+            return "(?:.{," + maximum + "})";
+
+        return null;
+    }
+
+    private static String _getPatternFromRegexValidator(RegexValidator regexValidator)
+    {
+        return regexValidator.getPattern();
     }
 }

Propchange: myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-examples/
------------------------------------------------------------------------------
--- svn:ignore (added)
+++ svn:ignore Fri Aug  6 21:35:08 2010
@@ -0,0 +1,4 @@
+.settings
+target
+.classpath
+.project

Modified: myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-examples/src/main/java/org/apache/myfaces/html5/examples/showcase/beans/InputTextBean.java
URL: http://svn.apache.org/viewvc/myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-examples/src/main/java/org/apache/myfaces/html5/examples/showcase/beans/InputTextBean.java?rev=983131&r1=983130&r2=983131&view=diff
==============================================================================
--- myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-examples/src/main/java/org/apache/myfaces/html5/examples/showcase/beans/InputTextBean.java
(original)
+++ myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-examples/src/main/java/org/apache/myfaces/html5/examples/showcase/beans/InputTextBean.java
Fri Aug  6 21:35:08 2010
@@ -24,7 +24,7 @@ import java.util.List;
 import javax.faces.bean.ManagedBean;
 import javax.faces.model.SelectItem;
 
-@ManagedBean(name="inputTextBean")
+@ManagedBean(name = "inputTextBean")
 public class InputTextBean
 {
 
@@ -43,6 +43,8 @@ public class InputTextBean
     private String movieName;
 
     private String someParam;
+    private String secondParam;
+    private String thirdParam;
 
     public List<SelectItem> getSuggestionItems()
     {
@@ -184,6 +186,26 @@ public class InputTextBean
         this.keyword = keyword;
     }
 
+    public String getSecondParam()
+    {
+        return secondParam;
+    }
+
+    public void setSecondParam(String secondParam)
+    {
+        this.secondParam = secondParam;
+    }
+
+    public String getThirdParam()
+    {
+        return thirdParam;
+    }
+
+    public void setThirdParam(String thirdParam)
+    {
+        this.thirdParam = thirdParam;
+    }
+
     public int getResult()
     {
         return ((firstNumber == null) ? 0 : firstNumber) * ((secondNumber == null) ? 0 :
secondNumber);

Modified: myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-examples/src/main/webapp/inputText/inputText04.xhtml
URL: http://svn.apache.org/viewvc/myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-examples/src/main/webapp/inputText/inputText04.xhtml?rev=983131&r1=983130&r2=983131&view=diff
==============================================================================
--- myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-examples/src/main/webapp/inputText/inputText04.xhtml
(original)
+++ myfaces/gsoc/html5-comp-lib/trunk/html5-comp-lib-examples/src/main/webapp/inputText/inputText04.xhtml
Fri Aug  6 21:35:08 2010
@@ -50,6 +50,11 @@
 			    	<hx:inputText id="textIT" value="#{inputTextBean.someParam}" title="A part number
is a digit followed by three uppercase letters.">
 			    		<f:validateRegex pattern="[0-9][A-Z]{3}" />
 			    	</hx:inputText>
+			    	
+			    	<label>Support for standard validators:</label>
+                    <hx:inputText id="anotherTextIT" value="#{inputTextBean.secondParam}"
required="true" title="A prefix is must be minimum 3 characters, maximum 5 characters.">
+                        <f:validateLength minimum="3" maximum="5" />
+                    </hx:inputText>
 		    	
 		    		<h:outputText />
 			    	<h:commandButton action="none"/>
@@ -59,7 +64,7 @@
 			<h:form id="myOtherForm">
 				<h:panelGrid cols="2" >
 			    	<label>Custom validation error handling:</label>
-			    	<hx:inputText id="otherTextIT" value="#{inputTextBean.someParam}" oninvalid="handleValidationError(event,
this);" 
+			    	<hx:inputText id="otherTextIT" value="#{inputTextBean.thirdParam}" oninvalid="handleValidationError(event,
this);" 
 			    		title="A part number is a digit followed by three uppercase letters.">
 			    		<f:validateRegex pattern="[0-9][A-Z]{3}" />
 			    	</hx:inputText>



Mime
View raw message