From hibernate-commits at lists.jboss.org Wed Sep 2 11:47:48 2009
Content-Type: multipart/mixed; boundary="===============2445757126768062887=="
MIME-Version: 1.0
From: hibernate-commits at lists.jboss.org
To: hibernate-commits at lists.jboss.org
Subject: [hibernate-commits] Hibernate SVN: r17469 -
validator/trunk/hibernate-validator/src/main/docbook/en-US/modules.
Date: Wed, 02 Sep 2009 11:47:48 -0400
Message-ID: <200909021547.n82Flm9I007335@svn01.web.mwc.hst.phx2.redhat.com>
--===============2445757126768062887==
Content-Type: text/plain; charset="utf-8"
MIME-Version: 1.0
Content-Transfer-Encoding: quoted-printable
Author: hardy.ferentschik
Date: 2009-09-02 11:47:47 -0400 (Wed, 02 Sep 2009)
New Revision: 17469
Modified:
validator/trunk/hibernate-validator/src/main/docbook/en-US/modules/custo=
mconstraints.xml
validator/trunk/hibernate-validator/src/main/docbook/en-US/modules/defin=
econstraints.xml
validator/trunk/hibernate-validator/src/main/docbook/en-US/modules/getti=
ngstarted.xml
validator/trunk/hibernate-validator/src/main/docbook/en-US/modules/using=
validator.xml
Log:
HV-220
Modified: validator/trunk/hibernate-validator/src/main/docbook/en-US/module=
s/customconstraints.xml
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D
--- validator/trunk/hibernate-validator/src/main/docbook/en-US/modules/cust=
omconstraints.xml 2009-09-02 13:24:17 UTC (rev 17468)
+++ validator/trunk/hibernate-validator/src/main/docbook/en-US/modules/cust=
omconstraints.xml 2009-09-02 15:47:47 UTC (rev 17469)
@@ -25,7 +25,7 @@
- Custom constraints
+ Creating custom constraints
=
Though the Bean Validation API defines a whole bunch of standard
constraint annotations such as @NotNull,
@@ -251,10 +251,10 @@
Using the constraint
=
Now that our first custom constraint is completed, we can use =
it
- in the Car class from the Getting started chapter =
to
- specify that the licensePlate field shall only
- contain upper-case strings:
+ in the Car class from the chapter to specify that the
+ licensePlate field shall only contain upper-case
+ strings:
=
package com.mycompany;
=
Modified: validator/trunk/hibernate-validator/src/main/docbook/en-US/module=
s/defineconstraints.xml
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D
--- validator/trunk/hibernate-validator/src/main/docbook/en-US/modules/defi=
neconstraints.xml 2009-09-02 13:24:17 UTC (rev 17468)
+++ validator/trunk/hibernate-validator/src/main/docbook/en-US/modules/defi=
neconstraints.xml 2009-09-02 15:47:47 UTC (rev 17469)
@@ -1,4 +1,4 @@
-
+
-
-
-
+
Defining constraints
=
@@ -38,7 +37,7 @@
element.
=
-
+ Built in constraints
=
Hibernate Validator comes with some built-in constraints, which
@@ -491,4 +490,4 @@
The name property will be checked for nullity when the Dog bean =
is
validated.
-
\ No newline at end of file
+
Modified: validator/trunk/hibernate-validator/src/main/docbook/en-US/module=
s/gettingstarted.xml
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D
--- validator/trunk/hibernate-validator/src/main/docbook/en-US/modules/gett=
ingstarted.xml 2009-09-02 13:24:17 UTC (rev 17468)
+++ validator/trunk/hibernate-validator/src/main/docbook/en-US/modules/gett=
ingstarted.xml 2009-09-02 15:47:47 UTC (rev 17469)
@@ -105,7 +105,7 @@
and Intellij have great built-in Maven support.
=
-
+ Class Car annotated with constraints
=
package com.mycompany;
@@ -127,7 +127,6 @@
private int seatCount;
=
public Car(String manufacturer, String licencePlate, int seatCount) {
-
this.manufacturer =3D manufacturer;
this.licensePlate =3D licencePlate;
this.seatCount =3D seatCount;
@@ -188,7 +187,6 @@
=
@Test
public void manufacturerIsNull() {
-
Car car =3D new Car(null, "DD-AB-123", 4);
=
Set<ConstraintViolation<Car>> constraintViolations =3D
@@ -200,7 +198,6 @@
=
@Test
public void licensePlateTooShort() {
-
Car car =3D new Car("Morris", "D", 4);
=
Set<ConstraintViolation<Car>> constraintViolations =3D =
@@ -212,7 +209,6 @@
=
@Test
public void seatCountTooLow() {
-
Car car =3D new Car("Morris", "DD-AB-123", 1);
=
Set<ConstraintViolation<Car>> constraintViolations =3D
@@ -224,7 +220,6 @@
=
@Test
public void carIsValid() {
-
Car car =3D new Car("Morris", "DD-AB-123", 2);
=
Set<ConstraintViolation<Car>> constraintViolations =3D
Modified: validator/trunk/hibernate-validator/src/main/docbook/en-US/module=
s/usingvalidator.xml
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D
--- validator/trunk/hibernate-validator/src/main/docbook/en-US/modules/usin=
gvalidator.xml 2009-09-02 13:24:17 UTC (rev 17468)
+++ validator/trunk/hibernate-validator/src/main/docbook/en-US/modules/usin=
gvalidator.xml 2009-09-02 15:47:47 UTC (rev 17469)
@@ -25,7 +25,7 @@
- Basic validation
+ Validation step by step
=
In this chapter we will see in more detail how to use Bean Validat=
ion
to validate constraints for a given entity model. We will also learn whi=
ch
@@ -34,7 +34,7 @@
to add constraints to an entity.
=
- Annotating your model
+ Defining constraints
=
Constraints in Bean Validation are expressed via Java annotation=
s.
In this section we show how to annotate an object model with these
@@ -42,30 +42,83 @@
constraint annotations - class-, field- and property-level
annotations.
=
-
- Not all constraints can be placed on any of these levels. In
- fact all the default constraints defined by Bean Validation cannot=
be
- places at class level. The java.lang.annotation.Target annotation
- placed on the constraint annotation itself determines on which
- elements a constraint can be placed. See also
-
+
+ Not all constraints can be placed on any of these levels. In f=
act
+ all the default constraints defined by Bean Validation cannot be pla=
ces
+ at class level. The java.lang.annotation.Target annotation placed on=
the
+ constraint annotation itself determines on which elements a constrai=
nt
+ can be placed. See also
+
=
Class-level
- annotations
+ constraints
=
- TODO
+ When a constraint annotation is placed on class level the class
+ instance itself passed to the
+ ConstraintValidator. Class level constraints =
are
+ useful if it is necessary to inspect more than a single property of =
the
+ class to validate it or if a correlation between different state
+ variables has to be evaluated. In the following example we add the
+ properties horsePower and
+ kiloWatt to the class Car.
+ We also add the constraint ValidCar to the class itself. We will lat=
er
+ see how we can actually create this custom constraint (see ). For now we can just ass=
ume
+ that this constraints will for example ensure that the value for
+ kiloWatt is 0.7456 *
+ horsePower.
+
+
+ Class Car with added horsePower and killoWatt
+ properties
+
+ package com.mycompany;
+
+import javax.validation.constraints.Min;
+import javax.validation.constraints.NotNull;
+import javax.validation.constraints.Size;
+
+@ValidCar
+public class Car {
+
+ @NotNull
+ private String manufacturer;
+
+ @NotNull
+ @Size(min =3D 2, max =3D 14)
+ private String licensePlate;
+
+ @Min(2)
+ private int seatCount;
+
+ private int horsePower;
+
+ private double kiloWatt;
+ =
+ public Car(String manufacturer, String licencePlate, int seatCount) {
+ this.manufacturer =3D manufacturer;
+ this.licensePlate =3D licencePlate;
+ this.seatCount =3D seatCount;
+ }
+
+ //getters and setters ...
+}
+
=
- Field level annotations
+ Field-level constraints
=
- One way for expressing constraints is to annotate the fields o=
f a
- class with constraint annotations. The following listing shows a sim=
ple
- example:
+ Constraints can also be expressed by annotating a field of a
+ class. The following listing shows a simple example:
=
- package com.mycompany;
+
+ Example for field level constraints
=
+ package com.mycompany;
+
import javax.validation.constraints.NotNull;
=
public class Car {
@@ -74,24 +127,32 @@
private String manufacturer;
=
public Car(String manufacturer) {
-
this.manufacturer =3D manufacturer;
}
}
+
+
+ When using field level constraints field access strategy is us=
ed
+ to access the value to be value. This means the bean validation prov=
ider
+ accesses the instance variable directly.
=
- Property level annotations
+ Property-level constraints
=
If your model class adheres to the JavaBeans
- standard (meaning basically, there are getter and setter methods for=
the
- properties of the class), it is also possible to annotate the proper=
ties
- of a bean class instead of its fields. Note that the property's gett=
er
- method has to be annotated, not its setter method:
+ standard, it is also possible to annotate the properties of a bean c=
lass
+ instead of its fields.
+ The property's getter method has to be annotated, not its
+ setter.
+
=
- package com.mycompany;
+
+ Example for property level constraints
=
+ package com.mycompany;
+
import javax.validation.constraints.AssertTrue;
import javax.validation.constraints.NotNull;
=
@@ -100,8 +161,7 @@
private String manufacturer;
=
private boolean isRegistered;
- =
- =
+ =
public Car(String manufacturer, boolean isRegistered) {
super();
this.manufacturer =3D manufacturer;
@@ -126,20 +186,21 @@
this.isRegistered =3D isRegistered;
}
}
+
=
- Generally it is considered a good practice to stick either with
- field or with property annotation within one mo=
del
- class for the sake of readability. It is not recommended to annotate=
a
- field and the accompanying getter method as this
- would cause the field to be validated twice.
+ When using property level constraints property access strategy=
is
+ used to access the value to be validated. This means the bean valida=
tion
+ provider accesses the state via the property accessor method.
=
- TODO: Make it explcit that where the difference lies between f=
iled
- and property level annotations. Depending where I place the annotati=
on
- the value to be validated gets accessed in different ways!
+ Generally it is recommended to stick either to field
+ or property annotation within one class. It is =
not
+ recommended to annotate a field and the
+ accompanying getter method as this would cause the field to be valid=
ated
+ twice.
=
- Annotated interfaces and super-classes
+ Constraint inheritance
=
When validating an object that implements an interface or exte=
nds
another class, all constraint annotations on the implemented interfa=
ce
@@ -147,33 +208,11 @@
on the validated object itself. To make things clearer let's have a =
look
at the following example:
=
- //class Car
-package com.mycompany;
+
+ Example for constraint inheritance using RentalCar
=
-import javax.validation.constraints.NotNull;
+ package com.mycompany;
=
-public class Car {
-
- private String manufacturer;
- =
- public Car(String manufacturer) {
- this.manufacturer =3D manufacturer;
- }
-
- @NotNull
- public String getManufacturer() {
- return manufacturer;
- }
-
- public void setManufacturer(String manufacturer) {
- this.manufacturer =3D manufacturer;
- }
-
-}
-
-//class RentalCar
-package com.mycompany;
-
import javax.validation.constraints.NotNull;
=
public class RentalCar extends Car {
@@ -193,16 +232,17 @@
public void setRentalStation(String rentalStation) {
this.rentalStation =3D rentalStation;
}
-
}
+
=
- Our well-known class Car is now extende=
d by
- RentalCar with an additional property,
- rentalStation. If an instance of
- RentalCar is validated now, not only the
- @NotNull constraint at the
- rentalStation property would be validated, but =
also
- the constraint at manufacturer from the parent
+ Our well-known class Car from the getting started section is =
now
+ extended by RentalCar with the additional
+ property rentalStation. If an instance of
+ RentalCar is validated, not only the
+ @NotNull constraint on
+ rentalStation would be validated, but also the
+ constraint at manufacturer from the parent
class.
=
The same would hold true, if Car was an
@@ -218,7 +258,7 @@
=
- Validating object graphs
+ Object graphs
=
The Bean Validation API does not only allow to validate single
objects but also complete object graphs. To do so just annotate a fi=
eld
@@ -228,7 +268,10 @@
@Valid will be validated as well (as will be
their children etc.). The following shows a simple example:
=
- //class Person
+
+ Class Person
+
+
package com.mycompany;
=
import javax.validation.constraints.NotNull;
@@ -250,12 +293,14 @@
public void setName(String name) {
this.name =3D name;
}
- =
-}
+}
+
=
-//class car
-package com.mycompany;
+
+ Adding a driver to the car
=
+ package com.mycompany;
+
import javax.validation.Valid;
import javax.validation.constraints.NotNull;
=
@@ -266,13 +311,12 @@
private Person driver;
=
public Car(Person driver) {
-
this.driver =3D driver;
}
=
//getters and setters ...
-
}
+
=
If an instance of Car is validated, the
referenced Person object will be validated as
@@ -291,14 +335,13 @@
=
- of type java.lang.Iterable (and
- therfore its direct or indirect derivations
- Collection, List a=
nd
- Set)
+ implement java.lang.Iterable
+ (especially Collection,
+ List and Set)
=
- of type java.util.Map
+ implement java.util.Map
=
@@ -306,8 +349,11 @@
cause each contained element to be validated, when the parent object=
is
validated.
=
- package com.mycompany;
+
+ Car with a list of passengers
=
+ package com.mycompany;
+
import java.util.ArrayList;
import java.util.List;
=
@@ -322,40 +368,78 @@
=
@NotNull
@Valid
- private List<Person> passengers =3D new ArrayList<=
;Person>();
+ private List<Person> passengers =3D new ArrayList<Person>(=
);
=
- public Car(List<Person> passengers) {
-
+ public Car(List<Person> passengers) {
this.passengers =3D passengers;
}
=
//getters and setters ...
-
}
+
=
If a Car instance is validated now, a
- ConstraintValidation will be raised, if any of
+ ConstraintValidation will be created, if any =
of
the Person objects contained in the
- passengers list has a null
- name.
+ passengers list has a null name.
+ null values are getting ignored when
+ validating object graphs.
+
=
- Validating your model
+ Validating constraints
=
The Validator interface is the main entry
- point to the Bean Validation API. In the following we first will show =
how
- to obtain Validator instances using the
- bootstrapping mechanism that the API provides. Afterwards you'll learn=
how
- to use the different methods of the Validator
- interfaces followed by an overview of the information that
- ConstraintViolation instances offer.
+ point to Bean Validation. In the following we first will show how to
+ obtain an Validator instance using the different
+ bootstrapping mechanisms. Afterwards we will learn how to use the
+ different methods of the Validator
+ interface.
=
- Obtaining Validator instances
+ Obtaining a Validator instance
=
- TODO: DefaultFactory, customization, note on thread safety
+ The first step towards validating a class instance is to get h=
old
+ of a Validator instance. The road to this
+ instance leads via the Validation class and a
+ ValidatorFactory. The by far easiest way is to
+ use the static
+ Validation.buildDefaultValidatorFactory()
+ method:ValidatorFactory factory =3D Validation.build=
DefaultValidatorFactory();
+Validator validator =3D factory.getValidator();You can al=
so use
+ the method Validation.byDefaultProvider() w=
hich
+ will allow you to configure several aspects of the created Validator
+ instance:Configuration<?> config =3D Validatio=
n.byDefaultProvider().configure();
+config.messageInterpolator(new MyMessageInterpolator())
+ .traversableResolver( new MyTraversableResolver())
+ .constraintValidatorFactory(new MyConstraintValidatorFactory());
+
+ValidatorFactory factory =3D config.buildValidatorFactory();
+Validator validator =3D factory.getValidator();
+We will learn more about
+ MessageInterpolator and
+ TraversableResolver in later chapters.
+
+ Last but not least you can ask for a Configuration object of a
+ specific Bean Validation provider. This is useful if you have more t=
han
+ one Bean Validation provider in your classpath. In this situation you
+ can make an explicit choice about which implementation to use. In the
+ case of Hibernate Validator the Validator creation looks
+ like:ValidatorConfiguration configuration =3D Valida=
tion.byProvider( HibernateValidator.class )
+config.messageInterpolator(new MyMessageInterpolator())
+ .traversableResolver( new MyTraversableResolver())
+ .constraintValidatorFactory(new MyConstraintValidatorFactory());
+
+ValidatorFactory factory =3D config.buildValidatorFactory();
+Validator validator =3D factory.getValidator();
+
+
+ The generated Validator instance is
+ thread safe and can be cached.
+ Now that we have a Validator instanc=
e,
+ let's see how we can use it to validate class instances.
=
@@ -449,8 +533,10 @@
=
- Validation groups
+ Using groups
=
+
+
Group sequences
=
@@ -458,7 +544,223 @@
=
-
-
+
+ Built-in constraints
+
+ Hibernate Validator comes with some built-in constraints, which
+ covers most basic data checks. As we'll see later, you're not limited =
to
+ them, you can literally in a minute write your own constraints.
+
+
+ Built-in constraints
+
+
+
+
+
+
+ Annotation
+
+ Apply on
+
+ Runtime checking
+
+ Hibernate Metadata impact
+
+
+
+
+
+ @Length(min=3D, max=3D)
+
+ property (String)
+
+ check if the string length match the range
+
+ Column length will be set to max
+
+
+
+ @Max(value=3D)
+
+ property (numeric or string representation of a
+ numeric)
+
+ check if the value is less than or equals to max
+
+ Add a check constraint on the column
+
+
+
+ @Min(value=3D)
+
+ property (numeric or string representation of a
+ numeric)
+
+ check if the value is more than or equals to min
+
+ Add a check constraint on the column
+
+
+
+ @NotNull
+
+ property
+
+ check if the value is not null
+
+ Column(s) are not null
+
+
+
+ @NotEmpty
+
+ property
+
+ check if the string is not null nor empty. Check if the
+ connection is not null nor empty
+
+ Column(s) are not null (for String)
+
+
+
+ @Past
+
+ property (date or calendar)
+
+ check if the date is in the past
+
+ Add a check constraint on the column
+
+
+
+ @Future
+
+ property (date or calendar)
+
+ check if the date is in the future
+
+ none
+
+
+
+ @Pattern(regex=3D"regexp", flag=3D) or @Patterns(
+ {@Pattern(...)} )
+
+ property (string)
+
+ check if the property match the regular expression give=
n a
+ match flag (see java.util.regex.Pattern
+ )
+
+ none
+
+
+
+ @Range(min=3D, max=3D)
+
+ property (numeric or string representation of a
+ numeric)
+
+ check if the value is between min and max
+ (included)
+
+ Add a check constraint on the column
+
+
+
+ @Size(min=3D, max=3D)
+
+ property (array, collection, map)
+
+ check if the element size is between min and max
+ (included)
+
+ none
+
+
+
+ @AssertFalse
+
+ property
+
+ check that the method evaluates to false (useful for
+ constraints expressed in code rather than annotations)
+
+ none
+
+
+
+ @AssertTrue
+
+ property
+
+ check that the method evaluates to true (useful for
+ constraints expressed in code rather than annotations)
+
+ none
+
+
+
+ @Valid
+
+ property (object)
+
+ perform validation recursively on the associated object=
. If
+ the object is a Collection or an array, the elements are valid=
ated
+ recursively. If the object is a Map, the value elements are
+ validated recursively.
+
+ none
+
+
+
+ @Email
+
+ property (String)
+
+ check whether the string is conform to the email address
+ specification
+
+ none
+
+
+
+ @CreditCardNumber
+
+ property (String)
+
+ check whether the string is a well formated credit card
+ number (derivative of the Luhn algorithm)
+
+ none
+
+
+
+ @Digits
+
+ property (numeric or string representation of a
+ numeric)
+
+ check whether the property is a number having up to
+ integerDigits integer digits and
+ fractionalDigits fractonal digits
+
+ define column precision and scale
+
+
+
+ @EAN
+
+ property (string)
+
+ check whether the string is a properly formated EAN or
+ UPC-A code
+
+ none
+
+
+
+