认识@Validated 和 @Valid

news2024/11/24 8:03:32

对于web应用来说,对方法参数的校验是十分重要的,参数校验的是否全面,直接决定整个方法的健壮性。
除了使用麻烦的if判断校验参数,还可以使用@Validated 和 @Valid注解来进行优雅地参数校验,让参数校验和写诗一样优雅。

@Validated 和 @Valid依赖引入

首先,我们来了解一下@Validated 和 @Valid 的区别。
在这里插入图片描述
虽然@Validated 和 @Valid 的提供者不同,但是两者都是由hibernate-validator来提供实现的,可以理解为@Validated是Spring对@Valid 的封装,增强了其功能。

所以,如果需要使用@Validated 和 @Valid注解来进行参数校验,则必须引入如下依赖:

<dependency>  
    <groupId>org.hibernate</groupId>  
    <artifactId>hibernate-validator</artifactId>  
    <version>6.0.1.Final</version>  
</dependency>

需要注意的是:如果spring-boot版本小于2.3.x,spring-boot-starter-web会自动传入hibernate-validator依赖。否则需要手动引入依赖。
另外,如果写法正确,但是校验机制没有生效,那么可能是hibernate-validator依赖的版本不对,可以百度查询当前Spring的版本适用的hibernate-validator版本号

常用校验注解混个眼熟

注解作用适用类型
@NotNull被注解的元素必须不为nullobject
@NotBlank验证注解的元素值不为空(不为null、去除首位空格后长度为0)String
@Length值长度在min和max区间内String
@Pattern必须符合指定的正则表达式String
@Email是Email格式String
------------
@AssertTrue必须为truebool
@AssertFalse必须是falsebool
------------
@Min其值必须大于等于最小值int,long,float,double
@Max其值必须小于等于最小值int,long,float,double
@DecimalMin其值必须大于等于最小值BigDecimal
@DecimalMax其值必须小于等于最小值BigDecimal
@Range元素值在最小值和最大值之间BigDecimal,BigInteger,CharSequence,byte,short,int,long
@Digits元素值的整数位数和小数位数上限float,double,BigDecimal
------------
@Past元素必须为过去的一个时间java.util.Date
@Future元素必须为未来的一个时间java.util.Date
------------
@Size元素的长度必须在指定范围内Array,List,Map
@NotEmpty元素值不为null且不为空Array,List,Map

错误提示语友好化

需要注意的是,SpringBoot2.3及其以上版本,会自动封装由@Validated 和 @Valid注解校验不通过时的异常,比如如下代码:

@RestController
@RequestMapping("/hello") 
public class HelloController {

    @PostMapping("/requestBodyValid")
    public UserDTO requestBodyValid(@RequestBody @Validated UserDTO userDTO){
        return userDTO;
    }
}


@Data
public class UserDTO {

    @NotNull(message = "id不能为空")
    @Min(value = 1, message = "id最小只能是1")
    private Long id;
}

此时请求接口,结果如下:
在这里插入图片描述
在这里插入图片描述
可见并没有返回校验失败的错误信息,查看应用日志,如下:
在这里插入图片描述
可见Spring对于校验发生的异常进行了封装,这使得前端调用方并不能看到具体的错误信息,十分不友好,所以这里我们使用Spring的统一异常处理机制@RestControllerAdvice 注解来统一对controller返回的异常进行友好化展示

@RestControllerAdvice注解的简单使用

@RestControllerAdvice
public class ExceptionHandler {

    @org.springframework.web.bind.annotation.ExceptionHandler({MethodArgumentNotValidException.class})
    @ResponseStatus(HttpStatus.OK)
    public ResultVO validExceptionHandle(MethodArgumentNotValidException exception){
        BindingResult bindingResult = exception.getBindingResult();
        StringBuilder errorMsg = new StringBuilder("校验失败:");
        for (FieldError fieldError : bindingResult.getFieldErrors()) {
            errorMsg.append(fieldError.getDefaultMessage()).append(";");
        }
        return new ResultVO()
                .setCode(ResultVO.VALID_NOT_PASS)
                .setMsg(errorMsg.toString())
                ;
    }
}

@Data
@Accessors(chain = true)
public class ResultVO {

    public static final String VALID_NOT_PASS = "40";

    public static final String VALID_PASS = "00";

    private String msg;

    private String code;
}

然后,我们再以相同的入参调用接口,可得到如下的返回值:
在这里插入图片描述
可见这样的提示信息就很友好化了。
下面是其他条件校验注解的简单使用:

@Data
public class UserDTO {

    @NotNull(message = "notNull校验")
    private Object notNull;

    @NotBlank(message = "notBlank校验")
    private String notBlank;

    @Length(min = 1, max = 10, message = "length(1--10)校验")
    private String length;

    @Pattern(regexp = "^\\d{2}$",message = "pattern(正则表达式匹配两位数字)校验")
    private String pattern;

    @Email(message = "email校验")
    private String email;

    @AssertFalse(message = "assertFalse校验")
    private Boolean assertFalse;

    @AssertTrue(message = "assertTrue校验")
    private Boolean assertTrue;


    @Min(value = 1, message = "min值是1-校验")
    private Integer min;

    @Max(value = 10, message = "max值是10-校验")
    private Integer max;

    @DecimalMin(value = "1.1", message = "decimalMin值是1.1-校验")
    private BigDecimal decimalMin;

    @DecimalMax(value = "10.1", message = "decimalMax值是10.1-校验")
    private BigDecimal decimalMax;

    @Range(min = 1, max = 10, message = "range(1--10)-校验")
    private Integer range;

    @Digits(integer = 2, fraction = 2, message = "digits(2,2)-校验")
    private Double digits;

    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
    @Past(message = "past校验")
    private Date past;

    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
    @Future(message = "future校验")
    private Date future;

    @Size(min = 1, max = 3, message = "size(1--3)校验")
    private List<Integer> size;

    @NotEmpty(message = "集合不能为null或者空集合")
    private List<Integer> notEmpty;
}

入参:

{
  "notBlank": "",
  "length": "123456789012",
  "pattern": "123",
  "email": "456aasd",
  "assertFalse": true,
  "assertTrue": false,
  "min": 0,
  "max": 11,
  "decimalMin": 1.0,
  "decimalMax": 10.2,
  "range": -1,
  "digits": 99.999,
  "past": "2024-06-25 21:04:18",
  "future": "2022-06-25 21:04:18",
  "size": [
    1,2,3,4
  ],
  "notEmpty": [
    
  ]
}

出参:
在这里插入图片描述
好了,今天就先到这里了,拜拜

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/685334.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

手机移动 APP测试流程及测试点

1 APP测试基本流程 1.1 流程图 1.2 测试周期 测试周期可按项目的开发周期来确定测试时间&#xff0c; 一般测试时间为两三 周(即 15 个工作日)&#xff0c;根据项目情况以及版本质量可适当缩短或延长 测试时间。正式测试前先向主管确认项目排期。 1.3 测试资源 测试任务开始…

移动云智能算力调度平台,谱写算力互联互通新篇章

中国移动算力网络建设取得新进展&#xff01;移动云智能算力调度平台验证了多云服务商间异构算力的统一调度能力&#xff0c;联动国家级超算中心、智算中心&#xff0c;促进东部业务灵活使用西部算力&#xff0c;作为未来算力互联网的统一调度平台将持续开展技术攻关与应用创新…

linux系统LNMP架构部署

文章目录 一、Nginx编译安装1、关闭防火墙&#xff0c;安全机制2、安装依赖包3、创建运行用户与组4、解压包、编译安装路径5、编译安装6、优化路径7、添加 Nginx 系统服务、赋权 二、安装 MySQL 服务1、安装环境依赖包2、创建运行用户与组3、解压包、编译安装路径4.编译安装5、…

chatgpt赋能python:用Python编程计算BMI,轻松掌握健康

用Python编程计算BMI&#xff0c;轻松掌握健康 作为一个现代人&#xff0c;保持健康的体态是我们每个人都需要关注的问题。那么&#xff0c;如何快速地计算自己的BMI呢&#xff1f;Python编程可以帮助我们轻松地实现这个目标。 什么是BMI&#xff1f; BMI全称为Body Mass In…

【Linux操作系统】互斥的4个概念以及认识信号量

文章目录 进程互斥的4个概念认识信号量认识接口理解IPC 信号量主要用于同步和互斥的&#xff0c;下面先来看看什么是同步和互斥。 进程互斥的4个概念 我们把大家都能看到的资源&#xff0c;称为公共资源。并且要想实现进程间通信&#xff0c;首要条件就是要让互相通信的进程看…

一文了解kubernetes部署:API部署过程

API部署 准备工作 一、镜像制作 请参考&#xff1a;《API镜像制作》 二、为k8s配置docker私服密钥 请参考&#xff1a;《配置docker私服密钥》 部署API 修改yaml文件 vi/opt/kubernetes/api/config-server.yaml vi/opt/kubernetes/api/api.yaml 1、修改api相应image值为您的镜…

【深度学习】日常笔记7

可以通过在⽹络中加⼊⼀个或多个隐藏层来克服线性模型的限制&#xff0c;使其能处理更普遍的函数关系类型。要做到这⼀点&#xff0c;最简单的⽅法是将许多全连接层堆叠在⼀起。每⼀层都输出到上⾯的层&#xff0c;直到⽣成最后的输出。 上面红框的公式其实换个角度是没错的。实…

总结911

目标规划&#xff1a; 月目标&#xff1a;6月&#xff08;线性代数强化9讲&#xff0c;考研核心词过三遍&#xff09; 周目标&#xff1a;线性代数强化5讲&#xff0c;英语背3篇文章并回诵&#xff0c;检测 每日规划 今日已做 1.回诵之前文章 2.每日长难句&#xff0c;句句…

Redis五种数据结构底层编码结构

String String是Redis中最常见的数据存储类型&#xff1a; 其基本编码方式是RAW&#xff0c;基于简单动态字符串&#xff08;SDS&#xff09;实现&#xff0c;存储上限为512mb。如果存储的SDS长度小于44字节&#xff0c;则会采用EMBSTR编码&#xff0c;此时object head与SDS是…

Mysql(Linux数据库或者在Navicate中)

Mysql数据库组成 服务端:主要存储数据,并接收用户发过来的SQL语句,并执行结果返回给客户端 客户端:下发用户要执行的sql语句,并显示服务器返回的执行结果 命令行数据库连接方式 mysql -h 数据库 IP -P 端口号 -u 数据库登录用户名 -p 数据库登录密码 -h不加表示为本机,-P不…

编译原理一:编译器工作流

文章目录 1. 编译器工作流1.1. 解析&#xff08;Parsing&#xff09;1.2. 遍历&#xff08;Traversal&#xff09;1.3 转换(Transformation)1.4 代码生成(Code Generation) 1. 编译器工作流 编译器是将一种语言转化为另一种语言的程序。在编译器工作流中&#xff0c;通常可以分…

git上传云效codeup

为了标识身份&#xff0c;建议先完成 Git 全局设置 git config --global user.name "xxx" git config --global user.email "xxxxxxqq.com" 1.删除本地 .git文件夹 2.云效上 添加库-新建代码库 3.在 git bash 里 按照 建好的代码库 下方的 命令行指引-…

chatgpt赋能python:Python编译成二进制文件:优化代码执行效率

Python编译成二进制文件&#xff1a;优化代码执行效率 介绍 随着Python编程的不断普及&#xff0c;越来越多的开发者选择Python作为开发工具。然而&#xff0c;Python解释器需要读取并解释源代码&#xff0c;这种解释方式在执行效率上存在瓶颈。为了提高执行效率&#xff0c;…

io.netty学习(十三)Netty 解码器

目录 前言 编解码概述 编解码器概述 Netty 内嵌的编码器 解码器 ByteToMessageDecoder 抽象类 ReplayingDecoder 抽象类 MessageToMessageDecoder 抽象类 总结 前言 编码和解码&#xff1a;数据从一种特定协议格式到另一种格式的转换。 处理编码和解码的程序通常被称…

【VulnHub系列】BrokenGallery

因为是从PDF转换过来偶尔可能会出现内容缺少&#xff0c;可以看原版PDF&#xff1a;有道云笔记 实验信息 Broken&#xff1a;192.168.10.111 Kali&#xff1a;192.168.10.106 实验过程 sudo arp-scan --interface eth0 192.168.10.1/24 然后对靶机进行端口探测 nmap -sT -…

定积分的应用—所围图形的面积、绕轴旋转所围成立体的体积、旋转曲面的面积、弧长

本篇本章&#xff0c;将从几个简单的例子带大家分析总结定积分的应用中常用的方法和思想&#xff0c;一起学习进入定积分的世界&#x1f61c;&#x1f61c; 一、求所围图形的面积 1.求由抛物线 y x 2 与 y 2 − x 2 所 围 图 形 的 面 积 yx^2与y2-x^2所围图形的面积 yx2与y2…

Windows下Android studio 搭建 android NDK 搭建 OLLVM 踩坑记录

1. 编译 ollvm-9.0.1 下载源码进行编译 https://github.com/heroims/obfuscator/tree/llvm-9.0.1 编译 这里有坑要注意 不能使用最新的 mingw 8.0.1 编译会报错 报错内容如下: PS D:\OLLVM\obfuscator-llvm-9.0.1\build> cmake -G "MinGW Makefiles" -DCMA…

浏览器 HTTPS 协议的相关知识点有哪些?

&#x1f482; 个人网站:【海拥】【游戏大全】【神级源码资源网】&#x1f91f; 前端学习课程&#xff1a;&#x1f449;【28个案例趣学前端】【400个JS面试题】&#x1f485; 寻找学习交流、摸鱼划水的小伙伴&#xff0c;请点击【摸鱼学习交流群】 目录 前言HTTPS协议的概念HT…

腾讯云私有云平台运维面试

文章目录 概述JD 岗位描述一面二面三面HR面 概述 根据会议将面试问题进行总结&#xff0c;很多问题感觉当时没回答好&#xff0c;这是为啥呢&#xff1f;应该还是不熟练吧&#xff0c;或者不善于表达。将次经历分享出来&#xff0c;大家多练练。 JD 岗位描述 私有云平台运维…

io.netty学习(十四)Netty 编码器

目录 前言 MessageToByteEncoder 抽象类 MessageToMessageEncoder 抽象类 总结 前言 上一篇我们讲解了解码器的相关知识&#xff0c;其中也提到了编码器的定义。 编码器就是用来把出站&#xff08;针对本身来讲&#xff0c;发送都是出站&#xff0c;接收都是入站&#xf…