package org.jboss.as.quickstarts.bean_validation.model;import java.io.Serializable;import javax.persistence.Column;import javax.persistence.Entity;import javax.persistence.GeneratedValue;import javax.persistence.Id;import javax.persistence.Table;import javax.validation.constraints.Digits;import javax.validation.constraints.NotNull;import javax.validation.constraints.Pattern;import javax.validation.constraints.Size;import javax.persistence.UniqueConstraint;import org.hibernate.validator.constraints.Email;import org.hibernate.validator.constraints.NotEmpty;@Entity@Table(name="MEMBER_BEAN_VALIDATION", uniqueConstraints = @UniqueConstraint(columnNames = "email"))public class Member implements Serializable { /** Default value included to remove warning. Remove or modify at will. **/ private static final long serialVersionUID = 1L; @Id @GeneratedValue private Long id; @NotNull @Size(min = 1, max = 25) @Pattern(regexp = "[A-Za-z ]*", message = "must contain only letters and spaces") private String name; @NotNull @NotEmpty @Email private String email; @NotNull @Size(min = 10, max = 12) @Digits(fraction = 0, integer = 12) //限制12位int数字,小数部分为0位. @Column(name = "phone_number") private String phoneNumber; public Long getId() { return id; } public void setId(Long id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; } public String getEmail() { return email; } public void setEmail(String email) { this.email = email; } public String getPhoneNumber() { return phoneNumber; } public void setPhoneNumber(String phoneNumber) { this.phoneNumber = phoneNumber; }}
如下代码自定义了一个名为email的约束(官方源码):
package org.hibernate.validator.constraints;import java.lang.annotation.Documented;import java.lang.annotation.Retention;import java.lang.annotation.Target;import javax.validation.Constraint;import javax.validation.Payload;import org.hibernate.validator.constraints.impl.EmailValidator;import static java.lang.annotation.ElementType.ANNOTATION_TYPE;import static java.lang.annotation.ElementType.CONSTRUCTOR;import static java.lang.annotation.ElementType.FIELD;import static java.lang.annotation.ElementType.METHOD;import static java.lang.annotation.ElementType.PARAMETER;import static java.lang.annotation.RetentionPolicy.RUNTIME;/** * The string has to be a well-formed email address. * * @author Emmanuel Bernard * @author Hardy Ferentschik */@Documented@Constraint(validatedBy = EmailValidator.class)@Target({ METHOD, FIELD, ANNOTATION_TYPE, CONSTRUCTOR, PARAMETER })@Retention(RUNTIME)public @interface Email { String message() default "{org.hibernate.validator.constraints.Email.message}"; Class [] groups() default { }; Class [] payload() default { }; /** * Defines several {@code @Email} annotations on the same element. */ @Target({ METHOD, FIELD, ANNOTATION_TYPE, CONSTRUCTOR, PARAMETER }) @Retention(RUNTIME) @Documented public @interface List { Email[] value(); }}
@Constraint(validatedBy = EmailValidator.class)的代码如下:
package org.hibernate.validator.constraints.impl;import java.util.regex.Matcher;import javax.validation.ConstraintValidator;import javax.validation.ConstraintValidatorContext;import org.hibernate.validator.constraints.Email;/** * Checks that a given string is a well-formed email address. ** The specification of a valid email can be found in * RFC 2822 * and one can come up with a regular expression matching * all valid email addresses as per specification. However, as this * article discusses it is not necessarily practical to * implement a 100% compliant email validator. This implementation is a trade-off trying to match most email while ignoring * for example emails with double quotes or comments. *
* * @author Emmanuel Bernard * @author Hardy Ferentschik */public class EmailValidator implements ConstraintValidator{ private static String ATOM = "[a-z0-9!#$%&'*+/=?^_`{|}~-]"; private static String DOMAIN = "(" + ATOM + "+(\\." + ATOM + "+)*"; private static String IP_DOMAIN = "\\[[0-9]{1,3}\\.[0-9]{1,3}\\.[0-9]{1,3}\\.[0-9]{1,3}\\]"; private java.util.regex.Pattern pattern = java.util.regex.Pattern.compile( "^" + ATOM + "+(\\." + ATOM + "+)*@" + DOMAIN + "|" + IP_DOMAIN + ")$", java.util.regex.Pattern.CASE_INSENSITIVE ); public void initialize(Email annotation) { } public boolean isValid(String value, ConstraintValidatorContext context) { if ( value == null || value.length() == 0 ) { return true; } Matcher m = pattern.matcher( value ); return m.matches(); }}
Validation API
- 开发者可以借助于ValidationAPI以编程的方式验证JavaBean。BeanValidationAPI的默认包是javax.validation。下面对该包中的一些类进行说明:
- ConstraintValidator:这是一个接口,具体的约束验证类需要实现该接口。该接口定义了相关的逻辑以验证给定对象类型中的约束。
- Validator:Validahttp://java.sun.com/javaee/6/docs/api/index.html?javax/validation/Validator.htmltor接口持有对象验证图的契约。该接口的实现必须是线程安全的。
- ConstraintViolation:ConstraintViolation接口表示给定bean上的约束验证失败,它公开了约束违背上下文以及描述该违背情况的信息。
- ValidationException:如果在验证过程中出现了某些不可恢复的错误就会抛出ValidationException异常。某些情况下可以指定该异常,如不合法的分组(group)定义、不合法的约束定义以及不合法的约束声明等等。
BeanValidation已经集成到了JSF2.0和JPA2.0中。在JSF中可以将表单输入域与域对象的属性绑定起来。JSF2和BeanValidation可以判断出绑定的是哪个属性并执行与之相关的验证,还会将约束违背的信息显示给用户。HibernateValidator4是BeanValidation规范的参考实现框架,其最新版增加了不少新特性,如分组验证、与JPA2和JSF2的自然集成以及扩展的注解集等等。
但是,所有的输入信息源头基本是用户,所以前台的验证才是最为关键的.