spring boot validation参数校验实例分析
作者:苍青浪 发布时间:2023-02-03 02:50:38
本文实例讲述了spring boot validation参数校验。分享给大家供大家参考,具体如下:
对于任何一个应用而言在客户端做的数据有效性验证都不是安全有效的,这时候就要求我们在开发的时候在服务端也对数据的有效性进行验证。 Spring Boot自身对数据在服务端的校验有一个比较好的支持,它能将我们提交到服务端的数据按照我们事先的约定进行数据有效性验证。
1 pom依赖
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-validation</artifactId>
</dependency>
2 校验使用实例
配置要验证的请求实体
public class User {
@Null
private Long id;
@NotBlank
private String name;
private String email;
// 省略getter和setter
}
控制器方法配置
@PostMapping("/addUser")
public String addUser(@Valid @RequestBody User user){
...
}
校验失败统一处理
校验失败时将抛出MethodArgumentNotValidException异常
/**
* 全局Exception处理
*
* @author liusq
*
*/
@RestControllerAdvice
public class GlobalExceptionHandler {
private static final Logger LOGGER = LoggerFactory.getLogger(GlobalExceptionHandler.class);
@SuppressWarnings("rawtypes")
@ExceptionHandler(value = Exception.class)
public ResponseEntity handle(Exception e) {
if (e instanceof MethodArgumentNotValidException) {
BindingResult bindingResult = ((MethodArgumentNotValidException) e).getBindingResult();
if (bindingResult.hasErrors() && bindingResult.hasFieldErrors()) {
FieldError fieldError = bindingResult.getFieldError();
BodyValidStatus bodyValidStatus = new BodyValidStatus.Builder().code("0009")
.message(fieldError.getDefaultMessage())
.field(fieldError.getField()).build();
LOGGER.warn(bodyValidStatus.getMessage() + e);
return new ResponseEntity<>(bodyValidStatus, HttpStatus.OK);
} else {
bodyStatus = DataUtil.bodyStatus("0009");
}
} else {
bodyStatus = DataUtil.bodyStatus(Constants.ERROR_CODE);
}
LOGGER.error(bodyStatus.getMessage() + e);
return new ResponseEntity<>(bodyStatus, HttpStatus.OK);
}
}
public class BodyValidStatus {
// 错误代码
private String code;
// 错误代码解释
private String message;
// 错误字段
private String field;
public BodyValidStatus() {
}
public BodyValidStatus(String code, String message, String field) {
this.code = code;
this.message = message;
this.field = field;
}
private BodyValidStatus(Builder builder) {
setCode(builder.code);
setMessage(builder.message);
setField(builder.field);
}
public String getCode() {
return code;
}
public void setCode(String code) {
this.code = code;
}
public String getMessage() {
return message;
}
public void setMessage(String message) {
this.message = message;
}
public String getField() {
return field;
}
public void setField(String field) {
this.field = field;
}
@Override
public String toString() {
return ToStringBuilder.reflectionToString(this);
}
public static final class Builder {
private String code;
private String message;
private String field;
public Builder() {
}
public Builder code(String val) {
code = val;
return this;
}
public Builder message(String val) {
message = val;
return this;
}
public Builder field(String val) {
field = val;
return this;
}
public BodyValidStatus build() {
return new BodyValidStatus(this);
}
}
}
3 验证注解详解
验证注解 | 验证的数据类型 | 说明 |
空检查 | ||
@Null | 任意类型 | 验证注解的元素值是null |
@NotNull | 任意类型 | 验证注解的元素不是null |
@NotBlank | CharSequence子类型(CharBuffer、String、StringBuffer、StringBuilder) | 验证注解的元素值不为空(不为null、去除首尾空格后长度不为0),不同于@NotEmpty,@NotBlank只应用于字符串且在比较时会去除字符串的首尾空格 |
@NotEmpty | CharSequence子类型、Collection、Map、数组 | 验证注解的元素值不为null且不为空(字符串长度不为0、集合大小不为0) |
Boolean检查 | ||
@AssertFalse | Boolean,boolean | 验证注解的元素值是false |
@AssertTrue | Boolean,boolean | 验证注解的元素值是true |
长度检查 | ||
@Size(min=下限, max=上限) | 字符串、Collection、Map、数组等 | 验证注解的元素值的在min和max(包含)指定区间之内,如字符长度、集合大小 |
@Length(min=下限, max=上限) | CharSequence子类型 | 验证注解的元素值长度在min和max区间内 |
日期检查 | ||
@Past | java.util.Date,java.util.Calendar;Joda Time类库的日期类型 | 验证注解的元素值(日期类型)比当前时间早 |
@Future | 与@Past要求一样 | 验证注解的元素值(日期类型)比当前时间晚 |
数值检查 | ||
@MIN(value=值) | BigDecimal,BigInteger, byte,short, int, long,等任何Number或CharSequence(存储的是数字)子类型 | 验证注解的元素值大于等于@Min指定的value值 |
@MAX(value=值) | 和@Min要求一样 | 验证注解的元素值小于等于@Max指定的value值 |
@DecimalMin(value=值) | 和@Min要求一样 | 验证注解的元素值大于等于@ DecimalMin指定的value值 |
@DecimalMax(value=值) | 和@Min要求一样 | 验证注解的元素值小于等于@ DecimalMax指定的value值 |
@Digits(integer=整数位数, fraction=小数位数) | 和@Min要求一样 | 验证注解的元素值的整数位数和小数位数上限 |
@Range(min=最小值, max=最大值) | BigDecimal,BigInteger,CharSequence, byte, short, int, long等原子类型和包装类型 | 验证注解的元素值在最小值和最大值之间 |
其他检查 | ||
@Valid | 任何非原子类型 | 指定递归验证关联的对象;如用户对象中有个地址对象属性,如果想在验证用户对象时一起验证地址对象的话,在地址对象上加@Valid注解即可级联验证 |
@Pattern(regexp=正则表达式,flag=标志的模式) | CharSequence的子类型 | 验证注解的元素值与指定的正则表达式匹配 |
@Email(regexp=正则表达式,flag=标志的模式) | CharSequence的子类型 | 验证注解的元素值是Email,也可以通过regexp和flag指定自定义的email格式 |
@CreditCardNumber | CharSequence的子类型 | 验证注解元素值是信用卡卡号 |
@ScriptAssert(lang= ,script=) | 业务类 | 校验复杂的业务逻辑 |
4 自定义验证注解和验证规则
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import javax.validation.Constraint;
import javax.validation.Payload;
import com.xxx.xxx.constraint.impl.MoneyValidator;
@Target({ElementType.FIELD, ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
@Constraint(validatedBy=MoneyValidator.class)
public @interface Money {
String message() default"不是金额形式";
Class<?>[] groups() default {};
Class<? extends Payload>[] payload() default {};
}
import java.util.regex.Pattern;
import javax.validation.ConstraintValidator;
import javax.validation.ConstraintValidatorContext;
import com.xxx.xxx.constraint.Money;
public class MoneyValidator implements ConstraintValidator<Money, Double> {
private String moneyReg = "^\\d+(\\.\\d{1,2})?$";//表示金额的正则表达式
private Pattern moneyPattern = Pattern.compile(moneyReg);
public void initialize(Money money) {
// TODO Auto-generated method stub
}
public boolean isValid(Double value, ConstraintValidatorContext arg1) {
// TODO Auto-generated method stub
if (value == null)
return true;
return moneyPattern.matcher(value.toString()).matches();
}
}
希望本文所述对大家java程序设计有所帮助。
来源:https://www.cnblogs.com/cangqinglang/p/11551912.html


猜你喜欢
- 本文主要为大家讲解多种Android调试工具的用法。 1. 查看当前
- 本文实例为大家分享了C#实现会移动的文字效果的具体代码,供大家参考,具体内容如下1 题目描述(1)Form1窗体设计界面如下:(2)窗体左侧
- 一. 概念简介在开始学习今天的知识之前,有必要先给大家讲解一下与今天内容相关的一些概念,否则可能会让一些小白产生迷惑。1. 日期和时间的区别
- 本案例通过使用JFileChooser实现对选定文件夹内图片实现自动播放和暂停播放代码如下,如有不合适的地方 还请指教package com
- 本文实例讲述了Android编程简单实现九宫格。分享给大家供大家参考,具体如下:实现的步骤1. 一个整体的容器部分。就是上图中包括整个图片项
- 一、项目运行环境配置:Jdk1.8 + Tomcat8.5 + mysql + Eclispe(IntelliJ IDEA,Eclispe,
- from jnius import autoclass>>> Stack = autoclass('java.ut
- 实现Android studio设置自动导包及自动导包快捷键方式一:Android studio只有导单个包的快捷键:Alt+Enter。方
- 在我们的程序当中如果要实现类似《360软件管家》的功能,就要解决两个问题,首先是要判断该程序已有一个实例在运行,其次是要将已运行的应用程序实
- 最近的项目里用到了,在网上找不到合适的,于是自己写了个简单的,带回弹效果:可以自定义的属性有:<!-- 滑动解锁控件 xml配置属性
- 本文为大家分享了C#基于Socket套接字的网络通信封装代码,供大家参考,具体内容如下摘要之所以要进行Socket套接字通信库封装,主要是直
- 场景最近在做数据分析项目,里面有这样一个业务:把匹配的数据打上标签,放到新的索引中。数据量:累计亿级的数据使用场景:可能会单次查询大量的数据
- IDEA快速创建getter和setter方法找到generate我的是Mac,右击鼠标就可以打开,相信windows也不难。选择gette
- 前言Docker旨在提供一种应用程序的自动化部署解决方案,在 Linux 系统上迅速创建一个容器(轻量级虚拟机)并部署和运行应用程序,并通过
- 因为一直用spring整合了mybatis,所以很少用到mybatis的session缓存。 习惯是本地缓存自己用map写或者引入第三方的本
- 下文笔者讲述SpringBoot配置log4j的方法分享,如下所示SpringBoot日志输出springboot框架中默认使用logbac
- 本文实例为大家分享了C#实现猜数字游戏具体代码,供大家参考,具体内容如下给定一个0-100的随机数字猜其大小题目样式:电脑产生一个0到100
- 安卓应用闪退后总会出现一个“抱歉,App已经停止运行”的弹窗,这样的用户体验并不好。很多大厂的App都去除了这个弹窗,因此本文主要介绍如何去
- Java中Static关键字的一些用法详解1. Static 修饰类属性,因为静态成员变量可以通过类名+属性名调用,非静态成员变量不能通过类
- 模拟新闻 APP 的界面1)写 ListView 之前先写布局: 这里有两种 Item 的布局:<?xml version=