校验器的知识点大致可以分为三个部分
- 第一部分介绍与校验功能相关的类
- 第二部分介绍校验器实现方式。
- 第三部分介绍如何获取校验结果。
1、相关类
Spring中使用Validator接口实现校验功能,它只有两个方法
- Supports:用于判断校验器适用于哪些对象。
- Validate:实现校验功能的逻辑,第一个参数为校验对象,第二个参数为校验的结果。
在数据绑定的功能中,校验只是其中的子功能,Spring使用DataBinder类实现数据绑定功能,该对象也可以触发校验功能,它包含一个或多个校验器,有List<Validator>属性。
Spring还提供了ValidationUtils,它是一个工具类,提供一些常见的方法,例如对象是否为空,字符串属性是否为NULL或空白字符。
注:Validator和DataBinder都有自己的类结构。
2、实现方式
Spring支持三种校验方式。
- 第一种是JSR-303相关的注解API,具体参考Hibernate Validator。
- 第二种是代码方式,使用Validator或者是DataBinder的validate方法。
- 第三种是数据绑定过程中自动触发,例如请求参数转换为Controller方法中的参数。
2.1 HibernateValidator
待补充。
2.2 代码方式
代码方式的步骤如下,
- 第一步,编写自定义校验器,实现Validator接口。示例中校验用户的姓名和年龄
public class UserValidator implements Validator {
public boolean supports(Class<?> clazz) {
return User.class.isAssignableFrom(clazz);
}
public void validate(Object target, Errors errors) {
// 判断姓名是否为空
ValidationUtils.rejectIfEmptyOrWhitespace(errors, "name", "姓名不能为空");
// 转换为User对象
User user = (User) target;
if (user.getAge() < 0) {
errors.rejectValue("age", "年龄不能小于0");
} else if (user.getAge() > 100) {
errors.rejectValue("age", "年龄不能大于100");
}
}
}
2.第二步,注册校验器,DataBinder方式是调用addValidator方法,Validator实现类方式是获取Validator实现类,可以直接new,也可以从IOC容器中获取。
调用Validator或者DataBinder的validate方法。代码如下:
-
DataBinder的validate方法,调用xxValidator的方法,添加,替换,删除校验器
/**
*
* @Title: testValidator
* @Description: 测试校验器,调用DataBinder的validate方法
*/
public static void testDataBinder() {
ApplicationContext context = getContext();
// 获取User对象
User user = context.getBean("singleton_user", User.class);
//
DataBinder binder = new DataBinder(user);
// 注册validator
binder.addValidators(new UserValidator());
// 校验
binder.validate();
// 获取结果
BindingResult result = binder.getBindingResult();
// 获取
List<FieldError> errors = result.getFieldErrors();
// 输出User对象
System.out.println(user.toString());
//
for (FieldError error : errors) {
System.out.println(error.getField() + ": " + error.getCode());
}
}
- Validator的validate方法,直接new,或者从IOC容器中获取。
/**
*
* @Title: testValidator
* @Description: 测试校验器
*/
public static void testValidator() {
ApplicationContext context = getContext();
// 获取User对象
User user = context.getBean("singleton_user", User.class);
// 创建UserValidator实例
UserValidator validator = new UserValidator();
// 创建Error对象
BindingResult result = new BeanPropertyBindingResult(user, "user");
// 校验
validator.validate(user, result);
// 输出User对象
System.out.println(user.toString());
// 输出校验结果
System.out.println(result.getFieldErrorCount());
}
上述方式是直接new创建Validator,从IOC容器中获取Validator的方式,XML方式下配置validator接口的实现类,注解方式下在实现类上添加@Component注解。
2.3 数据绑定
在数据绑定的过程中,可以添加校验器,实现校验功能。最常见的数据绑定过程是请求的参数转换为Controller类中方法的参数,这个过程是自动的。不过可以修改,添加自定义的过滤器
@Controller
public class MyController {
@InitBinder
protected void initBinder(WebDataBinder binder) {
// 添加自定义校验器,在方法中添加Errors参数对象,获取校验结果
binder.addValidators(new XXValidator());
}
// 请求参数转换为User对象, Errors对象获取校验结果
@GetMapping("/urlPath")
public String test(User user, Errors errors) {
return "您好 " + user.getName();
}
}
3、获取校验结果
当为代码方式时,当使用DataBinder的validate方法之后,可以调用getBindingResult对象返回结果对象,调用BindingResult对象的相关API可以获取校验的结果,这个接口继承Errors接口。
当使用Validator时,在使用validate方法之前,必须先创建一个Errors的实现类,在示例中我使用的BeanPropertyBindingResult,然后把该对象作为参数传入到validate方法中,之后调用它的API获取校验的结果。
当为数据绑定方式时,在请求参数转换为对象方法参数的过程中,可以在方法中添加Errors参数,之后调用它的API获取校验的结果。