Spring MVC 使用介绍(十六)数据验证 (三)分组、自定义、跨参数、其他
一、概述
除了依赖注入、方法参数,Bean Validation 1.1定义的功能还包括:
1、分组验证
2、自定义验证规则
3、类级别验证
4、跨参数验证
5、组合多个验证注解
6、其他
二、分组验证
通过分组,可实现不同情况下的不同验证规则,示例如下:
1、定义分组接口
public interface AddView {
}
public interface UpdateView {
}
2、定义实体
public class Person {
@Null(groups = AddView.class)
@NotNull(groups = {UpdateView.class, Default.class})
private Integer id;
...
}
注:不指定分组,即为Default分组
3、业务类
@Service
@Validated
public class PersonService {
@Validated(AddView.class)
public void addPerson(@Valid Person person) {} @Validated({UpdateView.class})
public void updatePerson(@Valid Person person) {} public void defaultOp(@Valid Person person) {}
}
4、测试
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = "classpath:spring-context.xml")
public class ValidTest {
@Autowired
private PersonService testService; @Test(expected = ConstraintViolationException.class)
public void test1() {
Person person = new Person();
person.setId(12);
testService.addPerson(person);
} @Test(expected = ConstraintViolationException.class)
public void test2() {
Person person = new Person();
testService.updatePerson(person);
} @Test(expected = ConstraintViolationException.class)
public void test3() {
Person person = new Person();
testService.defaultOp(person);
}
}
三、自定义验证规则
系统预定义的验证注解不能满足需求时,可自定义验证注解,示例如下:
1、自定义注解
@Target({ FIELD, METHOD, PARAMETER, ANNOTATION_TYPE })
@Retention(RUNTIME)
@Constraint(validatedBy = ForbiddenValidator.class)
@Documented
public @interface Forbidden {
//默认错误消息
String message() default "{forbidden.word}";
//分组
Class<?>[] groups() default { };
//负载
Class<? extends Payload>[] payload() default { };
//指定多个时使用
@Target({ FIELD, METHOD, PARAMETER, ANNOTATION_TYPE })
@Retention(RUNTIME)
@Documented
@interface List {
Forbidden[] value();
}
}
2、自定义注解处理类
public class ForbiddenValidator implements ConstraintValidator<Forbidden, String> {
private String[] forbiddenWords = {"admin"};
@Override
public void initialize(Forbidden constraintAnnotation) {
//初始化,得到注解数据
}
@Override
public boolean isValid(String value, ConstraintValidatorContext context) {
if(StringUtils.isEmpty(value)) {
return true;
}
for(String word : forbiddenWords) {
if(value.contains(word)) {
return false;//验证失败
}
}
return true;
}
}
3、默认错误消息
# format.properties
forbidden.word=包含敏感词汇
4、实体类
public class Person {
@Forbidden
private String name;
...
}
5、业务类
@Service
@Validated
public class PersonService {
public void defaultOp(@Valid Person person) { }
}
6、测试
@Test(expected = ConstraintViolationException.class)
public void test4() {
Person person = new Person();
person.setName("admin");
testService.defaultOp(person);
}
四、类级别验证
定义类级别验证,可实现对象中的多个属性组合验证,示例如下:
1、定义注解
@Target({ TYPE, ANNOTATION_TYPE})
@Retention(RUNTIME)
@Documented
@Constraint(validatedBy = CheckPasswordValidator.class)
public @interface CheckPassword {
//默认错误消息
String message() default "";
//分组
Class<?>[] groups() default { };
//负载
Class<? extends Payload>[] payload() default { };
//指定多个时使用
@Target({ FIELD, METHOD, PARAMETER, ANNOTATION_TYPE })
@Retention(RUNTIME)
@Documented
@interface List {
CheckPassword[] value();
}
}
2、定义处理类
public class CheckPasswordValidator implements ConstraintValidator<CheckPassword, Person> {
@Override
public void initialize(CheckPassword constraintAnnotation) {
}
@Override
public boolean isValid(Person person, ConstraintValidatorContext context) {
if(person == null) {
return true;
}
//没有填密码
if(!StringUtils.isEmpty(person.getNewPassword())) {
context.disableDefaultConstraintViolation();
context.buildConstraintViolationWithTemplate("{password.null}")
.addPropertyNode("password")
.addConstraintViolation();
return false;
}
if(!StringUtils.isEmpty(person.getConfirmPassword())) {
context.disableDefaultConstraintViolation();
context.buildConstraintViolationWithTemplate("{password.confirmation.null}")
.addPropertyNode("confirmation")
.addConstraintViolation();
return false;
}
//两次密码不一样
if (!person.getNewPassword().equals(person.getConfirmPassword())) {
context.disableDefaultConstraintViolation();
context.buildConstraintViolationWithTemplate("{password.confirmation.error}")
.addPropertyNode("confirmation")
.addConstraintViolation();
return false;
}
return true;
}
}
3、实体
@CheckPassword
public class Person {
private String newPassword;
private String confirmPassword;
...
}
4、业务类
@Service
@Validated
public class PersonService {
public void checkClassValidation(@Valid Person person) { }
}
5、测试
@Test(expected = ConstraintViolationException.class)
public void test4() {
Person person = new Person();
person.setNewPassword("asd");
person.setConfirmPassword("12132");
testService.checkClassValidation(person);
}
五、跨参数验证
使用跨参数验证,可实现方法级别中的多个参数组合验证,示例如下:
1、定义注解
@Constraint(validatedBy = CrossParameterValidator.class)
@Target({ METHOD, CONSTRUCTOR, ANNOTATION_TYPE })
@Retention(RUNTIME)
@Documented
public @interface CrossParameter {
String message() default "{password.confirmation.error}";
Class<?>[] groups() default { };
Class<? extends Payload>[] payload() default { };
}
2、定义处理类
@SupportedValidationTarget(ValidationTarget.PARAMETERS)
public class CrossParameterValidator implements ConstraintValidator<CrossParameter, Object[]> {
@Override
public void initialize(CrossParameter constraintAnnotation) {
} @Override
public boolean isValid(Object[] value, ConstraintValidatorContext context) {
if(value == null || value.length != 2) {
throw new IllegalArgumentException("must have two args");
}
if(value[0] == null || value[1] == null) {
return true;
}
if(value[0].equals(value[1])) {
return true;
}
return false;
}
}
3、业务类
@Service
@Validated
public class PersonService {
@CrossParameter
public void checkParaValidation(String pw1, String pw2) { }
}
4、测试
@Test(expected = ConstraintViolationException.class)
public void test5() {
testService.checkParaValidation("asd", "123");
}
六、组合多个验证注解
可将多个注解组合成一个注解,示例如下:
1、定义注解
@Target({ FIELD})
@Retention(RUNTIME)
@Documented
@NotNull
@Min(1)
@Constraint(validatedBy = { })
public @interface NotNullMin {
String message() default "";
Class<?>[] groups() default { };
Class<? extends Payload>[] payload() default { };
}
2、实体
public class Person {
@NotNullMin
private Integer id;
...
}
3、业务类
@Service
@Validated
public class PersonService {
public void checkCompositionValidation(@Valid Person person) { }
}
4、测试
@Test(expected = ConstraintViolationException.class)
public void test6() {
Person person = new Person();
testService.checkCompositionValidation(person);
}
七、其他
Bean Validation 1.1还支持本地化、脚本验证器,详细见参考文档
参考:
Spring4新特性——集成Bean Validation 1.1(JSR-349)到SpringMVC
Spring MVC 使用介绍(十六)数据验证 (三)分组、自定义、跨参数、其他的更多相关文章
- Spring MVC 使用介绍(六)—— 注解式控制器(二):请求映射与参数绑定
一.概述 注解式控制器支持: 请求的映射和限定 参数的自动绑定 参数的注解绑定 二.请求的映射和限定 http请求信息包含六部分信息: ①请求方法: ②URL: ③协议及版本: ④请求头信息(包括Co ...
- Spring MVC 使用介绍(十五)数据验证 (二)依赖注入与方法级别验证
一.概述 JSR-349 (Bean Validation 1.1)对数据验证进一步进行的规范,主要内容如下: 1.依赖注入验证 2.方法级别验证 二.依赖注入验证 spring提供BeanValid ...
- Spring MVC 使用介绍(十三)数据验证 (一)基本介绍
一.消息处理功能 Spring提供MessageSource接口用于提供消息处理功能: public interface MessageSource { String getMessage(Strin ...
- Spring MVC 使用介绍(十四)文件上传下载
一.概述 文件上传时,http请求头Content-Type须为multipart/form-data,有两种实现方式: 1.基于FormData对象,该方式简单灵活 2.基于<form> ...
- Spring MVC 使用介绍(十二)控制器返回结果统一处理
一.概述 在为前端提供http接口时,通常返回的数据需要统一的json格式,如包含错误码和错误信息等字段. 该功能的实现有四种可能的方式: AOP 利用环绕通知,对包含@RequestMapping注 ...
- spring(7)--注解式控制器的数据验证、类型转换及格式化
7.1.简介 在编写可视化界面项目时,我们通常需要对数据进行类型转换.验证及格式化. 一.在Spring3之前,我们使用如下架构进行类型转换.验证及格式化: 流程: ①:类型转换:首先调用Proper ...
- Spring MVC—数据绑定机制,数据转换,数据格式化配置,数据校验
Spring MVC数据绑定机制 数据转换 Spring MVC处理JSON 数据格式化配置使用 数据校验 数据校验 Spring MVC数据绑定机制 Spring MVC解析JSON格式的数据: 步 ...
- Spring MVC 3.0 返回JSON数据的方法
Spring MVC 3.0 返回JSON数据的方法1. 直接 PrintWriter 输出2. 使用 JSP 视图3. 使用Spring内置的支持// Spring MVC 配置<bean c ...
- Maven 工程下 Spring MVC 站点配置 (二) Mybatis数据操作
详细的Spring MVC框架搭配在这个连接中: Maven 工程下 Spring MVC 站点配置 (一) Maven 工程下 Spring MVC 站点配置 (二) Mybatis数据操作 这篇主 ...
- MySQL行(记录)的详细操作一 介绍 二 插入数据INSERT 三 更新数据UPDATE 四 删除数据DELETE 五 查询数据SELECT 六 权限管理
MySQL行(记录)的详细操作 阅读目录 一 介绍 二 插入数据INSERT 三 更新数据UPDATE 四 删除数据DELETE 五 查询数据SELECT 六 权限管理 一 介绍 MySQL数据操作: ...
随机推荐
- SLAM+语音机器人DIY系列:(三)感知与大脑——2.带自校准九轴数据融合IMU惯性传感器
摘要 在我的想象中机器人首先应该能自由的走来走去,然后应该能流利的与主人对话.朝着这个理想,我准备设计一个能自由行走,并且可以与人语音对话的机器人.实现的关键是让机器人能通过传感器感知周围环境,并通过 ...
- 远程连接桌面报:这可能是由于credssp加密oracle修正
1.Win+R 输入regedit打开注册表 找到对应的以下目录HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Polic ...
- Git 安装配置手册
Git 安装配置手册 首先我们要了解 Git 是类似于 SVN 用来管理项目的 首先要先下载 Git ,这个东西相当于一个核,是该功能的核心 下载地址(<https://gitforwindow ...
- 2019/1.7 js面向对象笔记
面向对象 1.构造函数里的属性怎么看?看this,谁前面有this谁就是属性. num不是属性,是私有作用域下的私有变量. 2.如何查找面向对象中的this 1.构造函数的this指向实例对象 2.如 ...
- CRM实施失败?请注意这6大问题及对策!
据Gartner调查显示:约50%的CRM项目不能达到客户期望.这一点与很多其他的IT项目状况非常类似,大多出于管理问题,供应商服务能力,项目执行不善等. 另据一个在线CRM论坛调查其失败的原因:67 ...
- 关于Java中基类构造器的调用问题
在<Java编程思想>第7章复用类中有这样一段话,值得深思.当子类继承了父类时,就涉及到了基类和导出类(子类)这两个类.从外部来看,导出类就像是一个与基类具有相同接口的新类,或许还会有一些 ...
- C#零基础入门-2-Visual Studio (VS)程序初始化及各组成部分
X:\Program Files (x86)\Microsoft Visual Studio 14.0\Common7\IDE\devenv.exe 可以使用桌面快捷方式启动,也可以从开始菜单启动,还 ...
- 自学MongoDB(1)
MongoDB是nosql(非关系型数据库)中的一种,面向文档的数据库,介于传统的结构化数据库(关系型数据库)与非关系型数据库(文件储存)之间的一种,具有数据结构非常松散和非常灵活的特点;常用于存储分 ...
- Audio播放
<audio controls="controls" id="warnAudio" hidden> <source src="~/m ...
- w3wp.exe进程占用内存过高解决方法
解决CPU占用过多: 1.在IIS中对每个网站进行单独的应用程序池配置.即互相之间不影响. 2.设置应用程序池的CPU监视,不超过25%(服务器为4CPU),每分钟刷新,超过限制时关闭. 根据w3wp ...