All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.opensymphony.xwork2.validator.Validator Maven / Gradle / Ivy

Go to download

XWork is an command-pattern framework that is used to power WebWork as well as other applications. XWork provides an Inversion of Control container, a powerful expression language, data type conversion, validation, and pluggable configuration.

There is a newer version: 2.1.3
Show newest version
/*
 * Copyright (c) 2002-2006 by OpenSymphony
 * All rights reserved.
 */
package com.opensymphony.xwork2.validator;


/**
 * 
 * 

The validators supplied by the Xwork distribution (and any validators you * might write yourself) come in two different flavors:

* *
    *
  1. Plain Validators / Non-Field validators
  2. *
  3. FieldValidators
  4. *
* *

Plain Validators (such as the ExpressionValidator) perform validation checks * that are not inherently tied to a single specified field. When you declare a * plain Validator in your -validation.xml file you do not associate a fieldname * attribute with it. (You should avoid using plain Validators within the * syntax described below.)

* *

FieldValidators (such as the EmailValidator) are designed to perform * validation checks on a single field. They require that you specify a fieldname * attribute in your -validation.xml file. There are two different (but equivalent) * XML syntaxes you can use to declare FieldValidators (see " vs. * syntax" below).

* *

There are two places where the differences between the two validator flavors * are important to keep in mind:

* *
    *
  1. when choosing the xml syntax used for declaring a validator * (either or )
  2. *
  3. when using the short-circuit capability
  4. *
* *

NOTE:Note that you do not declare what "flavor" of validator you are * using in your -validation.xml file, you just declare the name of the validator * to use and WebWork will know whether it's a "plain Validator" or a "FieldValidator" * by looking at the validation class that the validator's programmer chose * to implement.

* * * * * * *

To define validation rules for an Action, create a file named ActionName-validation.xml * in the same package as the Action. You may also create alias-specific validation rules which * add to the default validation rules defined in ActionName-validation.xml by creating * another file in the same directory named ActionName-aliasName-validation.xml. In both * cases, ActionName is the name of the Action class, and aliasName is the name of the * Action alias defined in the xwork.xml configuration for the Action.

* *

The framework will also search up the inheritance tree of the Action to * find validation rules for directly implemented interfaces and parent classes of the Action. * This is particularly powerful when combined with ModelDriven Actions and the VisitorFieldValidator. * Here's an example of how validation rules are discovered. Given the following class structure:

* *
    *
  • interface Animal;
  • *
  • interface Quadraped extends Animal;
  • *
  • class AnimalImpl implements Animal;
  • *
  • class QuadrapedImpl extends AnimalImpl implements Quadraped;
  • *
  • class Dog extends QuadrapedImpl;
  • *
* *

The framework method will look for the following config files if Dog is to be validated:

* *
    *
  • Animal
  • *
  • Animal-aliasname
  • *
  • AnimalImpl
  • *
  • AnimalImpl-aliasname
  • *
  • Quadraped
  • *
  • Quadraped-aliasname
  • *
  • QuadrapedImpl
  • *
  • QuadrapedImpl-aliasname
  • *
  • Dog
  • *
  • Dog-aliasname
  • *
* *

While this process is similar to what the XW:Localization framework does * when finding messages, there are some subtle differences. The most important * difference is that validation rules are discovered from the parent downwards. *

* *

NOTE:Child's *-validation.xml will add on to parent's *-validation.xml * according to the class hierarchi defined above. With this feature, one could have * more generic validation rule at the parent and more specific validation rule at * the child.

* * * * * *

There are two ways you can define validators in your -validation.xml file:

*
    *
  1. <validator>
  2. *
  3. <field-validator>
  4. *
*

Keep the following in mind when using either syntax:

* *

Non-Field-Validator * The <validator> element allows you to declare both types of validators * (either a plain Validator a field-specific FieldValidator).

* * *
 * 
 *    <!-- Declaring a plain Validator using the <validator> syntax: -->
 *
 *    <validator type="expression>
 *          <param name="expression">foo gt bar</param>
 *          <message>foo must be great than bar.</message>
 *    </validator>
 * 
 * 
* *
 * 
 *    <!-- Declaring a field validator using the <validator> syntax; -->
 *
 *    <validator type="required">
 *         <param name="fieldName">bar</param>
 *         <message>You must enter a value for bar.</message>
 *    </validator>
 * 
 * 
* * * *

field-validator * The <field-validator> elements are basically the same as the <validator> elements * except that they inherit the fieldName attribute from the enclosing <field> element. * FieldValidators defined within a <field-validator> element will have their fieldName * automatically filled with the value of the parent <field> element's fieldName * attribute. The reason for this structure is to conveniently group the validators * for a particular field under one element, otherwise the fieldName attribute * would have to be repeated, over and over, for each individual <validator>.

* *

HINT: * It is always better to defined field-validator inside a <field> tag instead of * using a <validator> tag and supplying fieldName as its param as the xml code itself * is clearer (grouping of field is clearer)

* *

NOTE: * Note that you should only use FieldValidators (not plain Validators) within a * block. A plain Validator inside a <field> will not be * allowed and would generate error when parsing the xml, as it is not allowed in * the defined dtd (xwork-validator-1.0.2.dtd)

* * *
 * 
 * Declaring a FieldValidator using the <field-validator> syntax:
 * 
 * <field name="email_address">
 *   <field-validator type="required">
 *       <message>You cannot leave the email address field empty.</message>
 *   </field-validator>
 *   <field-validator type="email">
 *       <message>The email address you entered is not valid.</message>
 *   </field-validator>
 * </field>
 * 
 * 
* * * *

The choice is yours. It's perfectly legal to only use elements * without the elements and set the fieldName attribute for each of them. * The following are effectively equal:

* * *
 * 
 * <field name="email_address">
 *   <field-validator type="required">
 *       <message>You cannot leave the email address field empty.</message>
 *   </field-validator>
 *   <field-validator type="email">
 *       <message>The email address you entered is not valid.</message>
 *   </field-validator>
 * </field>
 *
 *
 * <validator type="required">
 *   <param name="fieldName">email_address</param>
 *   <message>You cannot leave the email address field empty.</message>
 * </validator>
 * <validator type="email">
 *   <param name="fieldName">email_address</param>
 *   <message>The email address you entered is not valid.</message>
 * </validator>
 * 
 * 
* * * *

Beginning with XWork 1.0.1 (bundled with WebWork 2.1), it is possible * to short-circuit a stack of validators. Here is another sample config file * containing validation rules from the Xwork test cases: Notice that some of the * <field-validator> and <validator> elements have the short-circuit * attribute set to true.

* * *
 * <!-- START SNIPPET: exShortCircuitingValidators -->
 * <!DOCTYPE validators PUBLIC 
 *         "-//OpenSymphony Group//XWork Validator 1.0.2//EN" 
 *         "http://www.opensymphony.com/xwork/xwork-validator-1.0.2.dtd">
 * <validators>
 *   <!-- Field Validators for email field -->
 *   <field name="email">
 *       <field-validator type="required" short-circuit="true">
 *           <message>You must enter a value for email.</message>
 *       </field-validator>
 *       <field-validator type="email" short-circuit="true">
 *           <message>Not a valid e-mail.</message>
 *       </field-validator>
 *   </field>
 *   <!-- Field Validators for email2 field -->
 *   <field name="email2">
 *      <field-validator type="required">
 *           <message>You must enter a value for email2.</message>
 *       </field-validator>
 *      <field-validator type="email">
 *           <message>Not a valid e-mail2.</message>
 *       </field-validator>
 *   </field>
 *   <!-- Plain Validator 1 -->
 *   <validator type="expression">
 *       <param name="expression">email.equals(email2)</param>
 *       <message>Email not the same as email2</message>
 *   </validator>
 *   <!-- Plain Validator 2 -->
 *   <validator type="expression" short-circuit="true">
 *       <param name="expression">email.startsWith('mark')</param>
 *       <message>Email does not start with mark</message>
 *   </validator>
 * </validators>
 * <!-- END SNIPPET: exShortCircuitingValidators -->
 *
* * *

short-circuiting and Validator flavors

*

Plain validator takes precedence over field-validator. They get validated * first in the order they are defined and then the field-validator in the order * they are defined. Failure of a particular validator marked as short-circuit * will prevent the evaluation of subsequent validators and an error (action * error or field error depending on the type of validator) will be added to * the ValidationContext of the object being validated.

* *

In the example above, the actual execution of validator would be as follows:

* *
    *
  1. Plain Validator 1
  2. *
  3. Plain Validator 2
  4. *
  5. Field Validators for email field
  6. *
  7. Field Validators for email2 field
  8. *
* *

Since Field Validator 2 is short-circuited, if its validation failed, * it will causes Field validators for email field and Field validators for email2 * field to not be validated as well.

* *

Usefull Information: * More complecated validation should probably be done in the validate() * method on the action itself (assuming the action implements Validatable * interface which ActionSupport already does).

* *

* A plain Validator (non FieldValidator) that gets short-circuited will * completely break out of the validation stack no other validators will be * evaluated and plain validator takes precedence over field validator meaning * that they get evaluated in the order they are defined before field validator * gets a chance to be evaludated again according to their order defined. *

* * * * *

Short cuircuiting and validator flavours

*

A FieldValidator that gets short-circuited will only prevent other * FieldValidators for the same field from being evaluated. Note that this * "same field" behavior applies regardless of whether the or * syntax was used to declare the validation rule. * By way of example, given this -validation.xml file:

* * *
 * 
 * <validator type="required" short-circuit="true">
 *   <param name="fieldName">bar</param>
 *   <message>You must enter a value for bar.</message>
 * </validator>
 *
 * <validator type="expression">
 *   <param name="expression">foo gt bar</param>
 *   <message>foo must be great than bar.</message>
 * </validator>
 * 
 * 
* * *

both validators will be run, even if the "required" validator short-circuits. * "required" validators are FieldValidator's and will not short-circuit the plain * ExpressionValidator because FieldValidators only short-circuit other checks on * that same field. Since the plain Validator is not field specific, it is * not short-circuited.

* * * * *

As mentioned above, the framework will also search up the inheritance tree * of the action to find default validations for interfaces and parent classes of * the Action. If you are using the short-circuit attribute and relying on * default validators higher up in the inheritance tree, make sure you don't * accidentally short-circuit things higher in the tree that you really want!

* * * * @author Jason Carreira */ public interface Validator { void setDefaultMessage(String message); String getDefaultMessage(); String getMessage(Object object); void setMessageKey(String key); String getMessageKey(); /** * This method will be called before validate with a non-null ValidatorContext. * * @param validatorContext the validation context to use. */ void setValidatorContext(ValidatorContext validatorContext); ValidatorContext getValidatorContext(); /** * The validation implementation must guarantee that setValidatorContext will * be called with a non-null ValidatorContext before validate is called. * * @param object the object to be validated. * @throws ValidationException is thrown if there is validation error(s). */ void validate(Object object) throws ValidationException; /** * Sets the validator type to use (see class javadoc). * * @param type the type to use. */ void setValidatorType(String type); String getValidatorType(); }




© 2015 - 2024 Weber Informatics LLC | Privacy Policy