Struts 2
  1. Struts 2
  2. WW-600

Enable Client-side validation for visitor validations

    Details

    • Type: New Feature New Feature
    • Status: Closed
    • Priority: Major Major
    • Resolution: Fixed
    • Affects Version/s: WW 2.1
    • Fix Version/s: 2.3.15
    • Component/s: XML Validators
    • Labels:
      None
    • Environment:

      JDK 1.4.2, Tomcat 5.0.27, WebWork CVS (20040721)

      Description

      The client-side JavaScript doesn't work as advertised on:

      http://wiki.opensymphony.com/display/WW/Client-Side+Validation

      I have the following form:

      <ww:form action="'saveUser'" validate="true" cssClass="'detail'" method="'post'">

      This generates the following onsubmit handler:

      onsubmit="return($

      {parameters.name}_validate())"

      And the following JavaScript after the form:

      <script type="text/javascript">
      function ${parameters.name}

      _validate() {
      var form = document.forms['$

      {parameters.name}'];
      var focus = ${parameters.name}

      _validate_actual();
      if (focus != null) {
      form.elements[focus].focus();
      if (form.elements[focus].type == 'text' || form.elements[focus].type == 'textarea')

      { form.elements[focus].select(); }

      return false;
      } else

      { return true; }

      }

      function $

      {parameters.name}_validate_actual() {
      var form = document.forms['${parameters.name}

      '];
      // cannot find any applicable validators
      return null;
      }
      </script>

      If I add name="'user'" to the <ww:form>, then the JavaScript looks right, but I get:

      function user_validate_actual()

      { var form = document.forms['user']; // cannot find any applicable validators return null; }

      I have the following in validators.xml:

      <validator name="requiredstring"
      class="com.opensymphony.webwork.validators.JavaScriptRequiredStringValidator"/>

      Oddly enough, XMLBuddy (in Eclipse) says that "name" must be declared.

        Activity

        Hide
        Patrick Lightbody added a comment -

        Mark Woon has fixed most of this for the 2.1.1 release.

        Show
        Patrick Lightbody added a comment - Mark Woon has fixed most of this for the 2.1.1 release.
        Hide
        Patrick Lightbody added a comment -

        Mark is our new validation/javascript guru

        Show
        Patrick Lightbody added a comment - Mark is our new validation/javascript guru
        Hide
        Mark Woon added a comment -

        The first part is a problem with the documentation. The name attribute is required for client-side validation to work.

        As for the second problem, I need a bit more information. Matt, what validation rule(s) are you using? validators.xml only tells WW what validators are available. It doesn't actually set it up for use. You also need an ActionClass-validation.xml file with the validation rules (were ActionClass is the name of your Action class).

        The simplest way to test this is to see if validation works at all when you submit the form.

        Show
        Mark Woon added a comment - The first part is a problem with the documentation. The name attribute is required for client-side validation to work. As for the second problem, I need a bit more information. Matt, what validation rule(s) are you using? validators.xml only tells WW what validators are available. It doesn't actually set it up for use. You also need an ActionClass-validation.xml file with the validation rules (were ActionClass is the name of your Action class). The simplest way to test this is to see if validation works at all when you submit the form.
        Hide
        Patrick Lightbody added a comment -

        Matt,
        I haven't been able to reproduce this, even with the sample code you sent me. I'm going to go ahead and release WW 2.1.1 and then maybe afterwards we can look in to this some more.

        Show
        Patrick Lightbody added a comment - Matt, I haven't been able to reproduce this, even with the sample code you sent me. I'm going to go ahead and release WW 2.1.1 and then maybe afterwards we can look in to this some more.
        Hide
        Stefan Clos added a comment -

        i have the same question
        Environment: JDK 1.4.1, weblogic 8.1.2
        webwork-2.1.6,
        the action name is RegisterAction
        the name of validation file is
        "RegisterAction-validation.xml"
        content is:
        <validators>
        <field name="usrname">
        <field-validator type="requiredstring">
        <message>cant null</message>
        </field-validator>
        </field>
        <field name="password">
        <field-validator type="requiredstring">
        <message>must enter password</message>
        </field-validator>
        </field>
        <field name="salary">
        <field-validator type="requiredstring">
        <message>must enter salary</message>
        </field-validator>
        </field>
        </validators>

        Show
        Stefan Clos added a comment - i have the same question Environment: JDK 1.4.1, weblogic 8.1.2 webwork-2.1.6, the action name is RegisterAction the name of validation file is "RegisterAction-validation.xml" content is: <validators> <field name="usrname"> <field-validator type="requiredstring"> <message>cant null</message> </field-validator> </field> <field name="password"> <field-validator type="requiredstring"> <message>must enter password</message> </field-validator> </field> <field name="salary"> <field-validator type="requiredstring"> <message>must enter salary</message> </field-validator> </field> </validators>
        Hide
        Matt Raible added a comment -

        This still seems to be an issue with visitor validation in 2.2.1. Here's the JavaScript that's rendered in the final output when I have validate="true" on my form.

        <script>
        function customOnsubmit() {

        }
        </script>

        <script>
        function validateForm_signup()

        { form = document.getElementById("signup"); clearErrorMessages(form); clearErrorLabels(form); var errors = false; return !errors; }

        </script>

        Here's my SignupAction-validation.xml:

        <!DOCTYPE validators PUBLIC "-//OpenSymphony Group//XWork Validator 1.0//EN"
        "http://www.opensymphony.com/xwork/xwork-validator-1.0.dtd">
        <validators>
        <field name="user">
        <field-validator type="visitor">
        <param name="appendPrefix">false</param>
        <message/>
        </field-validator>
        </field>
        </validators>

        And here's my User-validation.xml (which works fine for server-side validation):

        <!DOCTYPE validators PUBLIC "-//OpenSymphony Group//XWork Validator 1.0.2//EN"
        "http://www.opensymphony.com/xwork/xwork-validator-1.0.2.dtd">
        <validators>
        <field name="user.username">
        <field-validator type="requiredstring">
        <message key="errors.required"/>
        </field-validator>
        </field>
        <field name="user.password">
        <field-validator type="requiredstring">
        <message key="errors.required"/>
        </field-validator>
        </field>
        <field name="user.confirmPassword">
        <field-validator type="requiredstring">
        <message key="errors.required"/>
        </field-validator>
        <field-validator type="fieldexpression">
        <param name="expression">
        (user.confirmPassword.equals(user.password))
        </param>
        <message key="errors.twofields"/>
        </field-validator>
        </field>
        <field name="user.firstName">
        <field-validator type="requiredstring">
        <message key="errors.required"/>
        </field-validator>
        </field>
        <field name="user.lastName">
        <field-validator type="requiredstring">
        <message key="errors.required"/>
        </field-validator>
        </field>
        <field name="user.address.city">
        <field-validator type="requiredstring">
        <message key="errors.required"/>
        </field-validator>
        </field>
        <field name="user.address.province">
        <field-validator type="requiredstring">
        <message key="errors.required"/>
        </field-validator>
        </field>
        <field name="user.address.country">
        <field-validator type="requiredstring">
        <message key="errors.required"/>
        </field-validator>
        </field>
        <field name="user.address.postalCode">
        <field-validator type="requiredstring">
        <message key="errors.required"/>
        </field-validator>
        <!-- Can't get regex validation to work -->
        <!--field-validator type="fieldexpression">
        <param name="expression">
        user.postalCode.matches('^\d

        {5}

        \d*$'))
        </param>
        <message key="errors.zip"/>
        </field-validator-->
        </field>
        <field name="user.email">
        <field-validator type="requiredstring">
        <message key="errors.required"/>
        </field-validator>
        <field-validator type="email">
        <message key="errors.email"/>
        </field-validator>
        </field>
        <!-- Can't get regex validation to work -->
        <!--field name="user.phoneNumber">
        <field-validator type="fieldexpression">
        <param name="expression">
        (user.phoneNumber.matches('^(?(\d

        {3}))?[-| ]?(\d{3}

        )[-| ]?(\d

        {4}

        )$'))
        </param>
        <message key="errors.phone"/>
        </field-validator>
        </field-->
        <field name="user.website">
        <field-validator type="requiredstring">
        <message key="errors.required"/>
        </field-validator>
        </field>
        <field name="user.passwordHint">
        <field-validator type="requiredstring">
        <message key="errors.required"/>
        </field-validator>
        </field>
        </validators>

        Show
        Matt Raible added a comment - This still seems to be an issue with visitor validation in 2.2.1. Here's the JavaScript that's rendered in the final output when I have validate="true" on my form. <script> function customOnsubmit() { } </script> <script> function validateForm_signup() { form = document.getElementById("signup"); clearErrorMessages(form); clearErrorLabels(form); var errors = false; return !errors; } </script> Here's my SignupAction-validation.xml: <!DOCTYPE validators PUBLIC "-//OpenSymphony Group//XWork Validator 1.0//EN" "http://www.opensymphony.com/xwork/xwork-validator-1.0.dtd"> <validators> <field name="user"> <field-validator type="visitor"> <param name="appendPrefix">false</param> <message/> </field-validator> </field> </validators> And here's my User-validation.xml (which works fine for server-side validation): <!DOCTYPE validators PUBLIC "-//OpenSymphony Group//XWork Validator 1.0.2//EN" "http://www.opensymphony.com/xwork/xwork-validator-1.0.2.dtd"> <validators> <field name="user.username"> <field-validator type="requiredstring"> <message key="errors.required"/> </field-validator> </field> <field name="user.password"> <field-validator type="requiredstring"> <message key="errors.required"/> </field-validator> </field> <field name="user.confirmPassword"> <field-validator type="requiredstring"> <message key="errors.required"/> </field-validator> <field-validator type="fieldexpression"> <param name="expression"> (user.confirmPassword.equals(user.password)) </param> <message key="errors.twofields"/> </field-validator> </field> <field name="user.firstName"> <field-validator type="requiredstring"> <message key="errors.required"/> </field-validator> </field> <field name="user.lastName"> <field-validator type="requiredstring"> <message key="errors.required"/> </field-validator> </field> <field name="user.address.city"> <field-validator type="requiredstring"> <message key="errors.required"/> </field-validator> </field> <field name="user.address.province"> <field-validator type="requiredstring"> <message key="errors.required"/> </field-validator> </field> <field name="user.address.country"> <field-validator type="requiredstring"> <message key="errors.required"/> </field-validator> </field> <field name="user.address.postalCode"> <field-validator type="requiredstring"> <message key="errors.required"/> </field-validator> <!-- Can't get regex validation to work --> <!--field-validator type="fieldexpression"> <param name="expression"> user.postalCode.matches('^\d {5} \d*$')) </param> <message key="errors.zip"/> </field-validator--> </field> <field name="user.email"> <field-validator type="requiredstring"> <message key="errors.required"/> </field-validator> <field-validator type="email"> <message key="errors.email"/> </field-validator> </field> <!-- Can't get regex validation to work --> <!--field name="user.phoneNumber"> <field-validator type="fieldexpression"> <param name="expression"> (user.phoneNumber.matches('^(?(\d {3}))? [-| ] ?(\d{3} ) [-| ] ?(\d {4} )$')) </param> <message key="errors.phone"/> </field-validator> </field--> <field name="user.website"> <field-validator type="requiredstring"> <message key="errors.required"/> </field-validator> </field> <field name="user.passwordHint"> <field-validator type="requiredstring"> <message key="errors.required"/> </field-validator> </field> </validators>
        Hide
        Claus Ibsen added a comment -

        I tired the showcase from CVS HEAD and the pure clientside validation worked there. But I don't think it uses the Visitor validation.

        I think that in 2.2.1 the showcase pure clientside validation did not work.

        At least my own little app didn't work with 2.21 but with CVS HEAD.

        Show
        Claus Ibsen added a comment - I tired the showcase from CVS HEAD and the pure clientside validation worked there. But I don't think it uses the Visitor validation. I think that in 2.2.1 the showcase pure clientside validation did not work. At least my own little app didn't work with 2.21 but with CVS HEAD.
        Hide
        Patrick Lightbody added a comment -

        Matt,
        We're on a time crunch to fix 2.2.2 before we go in to the Struts incubator. Basically, the gist of this issue is that pure client side validation (as opposed to ajax style) only supports very basic validation rules. That means that visitor rules won't work until we spend more time on it

        I have to push this back to 2.3 (aka Struts Action 2.0), but if you want to try to hack at form-close-validate.ftl, you might be able to get support in there.

        Show
        Patrick Lightbody added a comment - Matt, We're on a time crunch to fix 2.2.2 before we go in to the Struts incubator. Basically, the gist of this issue is that pure client side validation (as opposed to ajax style) only supports very basic validation rules. That means that visitor rules won't work until we spend more time on it I have to push this back to 2.3 (aka Struts Action 2.0), but if you want to try to hack at form-close-validate.ftl, you might be able to get support in there.
        Hide
        Don Brown added a comment -

        So where do we sit? Is it still a problem or does it work as advertised? If it is an issue, will anyone sign up to fix it for 2.0.0?

        Show
        Don Brown added a comment - So where do we sit? Is it still a problem or does it work as advertised? If it is an issue, will anyone sign up to fix it for 2.0.0?
        Hide
        Matt Raible added a comment -

        It still doesn't work if you put your validation rules on your model objects (i.e. User-validation.xml), but it does work if you put the validation rules next to your action (i.e. UserAction-validation.xml). Witness it in action with WebWork 2.2.2 at http://demo.appfuse.org/appfuse-webwork/signup.html.

        Source code for JSP at: http://fisheye5.cenqua.com/browse/~raw,r=1.9/appfuse/extras/webwork/web/pages/signup.jsp

        Show
        Matt Raible added a comment - It still doesn't work if you put your validation rules on your model objects (i.e. User-validation.xml), but it does work if you put the validation rules next to your action (i.e. UserAction-validation.xml). Witness it in action with WebWork 2.2.2 at http://demo.appfuse.org/appfuse-webwork/signup.html . Source code for JSP at: http://fisheye5.cenqua.com/browse/~raw,r=1.9/appfuse/extras/webwork/web/pages/signup.jsp
        Hide
        Don Brown added a comment -

        I'm bumping it over to 2.0.1, as I'm unable to replicate it right now, but want to look at it further.

        Show
        Don Brown added a comment - I'm bumping it over to 2.0.1, as I'm unable to replicate it right now, but want to look at it further.
        Hide
        Ted Husted added a comment -

        Bumping issues to 2.1.x, except those that involve backward-compatability with Struts 1 or WebWork 2.

        Show
        Ted Husted added a comment - Bumping issues to 2.1.x, except those that involve backward-compatability with Struts 1 or WebWork 2.
        Hide
        Don Brown added a comment -

        At this point, it looks like yes, we don't support client-side validations for visitor validators. Therefore, I've updated the docs to that effect and have changed this ticket to be a feature request, rather than a bug.

        Show
        Don Brown added a comment - At this point, it looks like yes, we don't support client-side validations for visitor validators. Therefore, I've updated the docs to that effect and have changed this ticket to be a feature request, rather than a bug.
        Hide
        Lukasz Racon added a comment -

        Attached is patch for the form tag that enables javascript visitor validation. Tested on 2.1.7/2.1.8-SNAPSHOT with annotation validators. Tag decomposes visitor validator into a list of sub validators - this way it all existing javascript validators are reused.

        Fixed issues:

        • javascript validation for visitor validator, including nested visitors (supports appendPrefix)
        • fixes validation for radio, checkbox, select input fields (field.value does not work with validation for these input fields)
        • fixes validation for annotated methods (WW-2191) - when actionMethod is provided via form tag's action attribute FormTag returns validators for given method only, instead of all action's validators.
        Show
        Lukasz Racon added a comment - Attached is patch for the form tag that enables javascript visitor validation. Tested on 2.1.7/2.1.8-SNAPSHOT with annotation validators. Tag decomposes visitor validator into a list of sub validators - this way it all existing javascript validators are reused. Fixed issues: javascript validation for visitor validator, including nested visitors (supports appendPrefix) fixes validation for radio, checkbox, select input fields (field.value does not work with validation for these input fields) fixes validation for annotated methods ( WW-2191 ) - when actionMethod is provided via form tag's action attribute FormTag returns validators for given method only, instead of all action's validators.
        Hide
        Lukasz Racon added a comment -

        Same patch as above but with granted license to ASF.

        Show
        Lukasz Racon added a comment - Same patch as above but with granted license to ASF.
        Hide
        Lukasz Lenart added a comment -

        Patch applied, thanks!

        As this a bit problematic issue it needs extensive testing

        Show
        Lukasz Lenart added a comment - Patch applied, thanks! As this a bit problematic issue it needs extensive testing
        Hide
        Hudson added a comment -

        Integrated in Struts2-JDK6 #712 (See https://builds.apache.org/job/Struts2-JDK6/712/)
        WW-600 Enables Client-side validation for visitor validations (Revision 1485978)

        Result = SUCCESS
        lukaszlenart :
        Files :

        • /struts/struts2/trunk/core/src/main/java/org/apache/struts2/components/Form.java
        • /struts/struts2/trunk/core/src/main/resources/template/xhtml/form-close-validate.ftl
        • /struts/struts2/trunk/core/src/test/java/org/apache/struts2/components/FormTest.java
        • /struts/struts2/trunk/core/src/test/resources/org/apache/struts2/views/jsp/ui/Formtag-2.txt
        • /struts/struts2/trunk/core/src/test/resources/org/apache/struts2/views/jsp/ui/Formtag-22.txt
        • /struts/struts2/trunk/core/src/test/resources/org/apache/struts2/views/jsp/ui/Formtag-24.txt
        Show
        Hudson added a comment - Integrated in Struts2-JDK6 #712 (See https://builds.apache.org/job/Struts2-JDK6/712/ ) WW-600 Enables Client-side validation for visitor validations (Revision 1485978) Result = SUCCESS lukaszlenart : Files : /struts/struts2/trunk/core/src/main/java/org/apache/struts2/components/Form.java /struts/struts2/trunk/core/src/main/resources/template/xhtml/form-close-validate.ftl /struts/struts2/trunk/core/src/test/java/org/apache/struts2/components/FormTest.java /struts/struts2/trunk/core/src/test/resources/org/apache/struts2/views/jsp/ui/Formtag-2.txt /struts/struts2/trunk/core/src/test/resources/org/apache/struts2/views/jsp/ui/Formtag-22.txt /struts/struts2/trunk/core/src/test/resources/org/apache/struts2/views/jsp/ui/Formtag-24.txt

          People

          • Assignee:
            Lukasz Lenart
            Reporter:
            Matt Raible
          • Votes:
            0 Vote for this issue
            Watchers:
            5 Start watching this issue

            Dates

            • Created:
              Updated:
              Resolved:

              Development