【Java】Sping Boot中使用Javax Bean Validation

目录

  • Javax Bean Validation
  • 在Spring Boot中集成Javax Bean Validation
  • 使用案例
  • 功能测试
  • 配置全局异常处理器
  • 重新测试
  • 返回特定形式的信息
    • 方式一
    • 方式二
  • 附:常用的注解

Javax Bean Validation

Javax Bean Validation是Java平台的一项规范,旨在提供一种简单且可扩展的方式来验证Java对象的数据。它提供了一组注解,可以应用于Java Bean的属性上,以定义验证规则,并提供了一组验证器来执行这些规则。

在Spring Boot中集成Javax Bean Validation

本文基于SSM框架(可参考博客:【Java】使用IntelliJ IDEA搭建SSM(MyBatis-Plus)框架并连接MySQL数据库)

Spring Boot对Javax Bean Validation提供了内置支持。

在pom.xml文件中添加依赖(包含在标签dependencies中):

<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-validation</artifactId>
</dependency>
<dependency><groupId>javax.validation</groupId><artifactId>validation-api</artifactId><version>2.0.1.Final</version>
</dependency>
<dependency><groupId>org.apache.tomcat.embed</groupId><artifactId>tomcat-embed-el</artifactId><version>9.0.83</version>
</dependency>

这些依赖会自动包含Javax Bean Validation API以及Hibernate Validator作为实现。
其中spring-boot-starter-validation的版本由其parent确定:

<!-- 定义父项目,使用Spring Boot 的版本管理 --><parent><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-parent</artifactId><version>2.7.17</version><relativePath/> <!-- lookup parent from repository --></parent>

使用案例

以用户注册功能为例,验证用户输入的用户名和密码。

  1. 创建一个名为User的Java实体类:
import lombok.Data;
import javax.validation.constraints.Size;
import javax.validation.constraints.NotBlank;@Data
public class User {@NotBlank(message = "用户名不能为空")private String username;@Size(min = 6, message = "密码长度不能少于6位")private String password;
}

在User类中,使用了@NotBlank@Size注解来定义了对用户名和密码的验证规则。

  1. 创建UserMapper,UserMapperxml,UserService,UserServiceImpl
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.z.entity.User;
import org.apache.ibatis.annotations.Mapper;@Mapper
public interface UserMapper extends BaseMapper<User> {
}
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.z.mapper.UserMapper">
</mapper>
import com.baomidou.mybatisplus.extension.service.IService;
import com.z.entity.User;public interface UserService extends IService<User> {
}
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.z.entity.User;
import com.z.mapper.UserMapper;
import com.z.service.UserService;
import org.springframework.stereotype.Service;@Service
public class UserServiceImpl extends ServiceImpl<UserMapper, User> implements UserService {
}
  1. 创建一个REST控制器来处理用户注册请求:
import com.z.entity.User;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RestController;import javax.validation.Valid;@RestController
public class UserController {@PostMapping("/register")public ResponseEntity<String> registerUser(@RequestBody @Valid User user) {// 处理用户注册逻辑return ResponseEntity.ok("用户注册成功");}
}

在UserController中,使用了@Valid注解来告诉Spring Boot验证User对象,并通过@RequestBody注解将请求体映射到User对象上。

  1. 新建一个数据库及与实体类对应的数据表,并配置数据库:

在resources下添加application.yml文件:

server:# 端口port: 8080spring:# 数据源配置datasource:driver-class-name: com.mysql.cj.jdbc.Driverurl: jdbc:mysql://localhost:3306/yourdatabase?characterEncoding=utf-8username: yourusernamepassword: yourpasswordjackson:time-zone: GMT+8date-format: yyyy-MM-dd HH:mm:ssmybatis-plus:# mapper文件映射路径mapper-locations: classpath*:mapper/*.xmlconfiguration:# 打印SQL语句log-impl: org.apache.ibatis.logging.stdout.StdOutImpl

其中,yourusername,yourpassword,yourdatabase注意换成自己的。

  1. 编写Main.java运行项目,并通过IDEA的启动按钮启动项目:
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;@SpringBootApplication
public class Main {public static void main(String[] args) {SpringApplication.run(Main.class, args);}
}

功能测试

使用Postman发送以下JSON请求体:
在这里插入图片描述

点击send,接收到一个400 Bad Request响应:

在这里插入图片描述
可以观察到,之前写在注解中的message并没有展示,需配置全局异常处理器处理异常。

配置全局异常处理器

创建一个@ControllerAdvice类,并在其中定义一个方法来处理MethodArgumentNotValidException异常:

import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.MethodArgumentNotValidException;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;@ControllerAdvice
public class GlobalExceptionHandler {@ExceptionHandler(MethodArgumentNotValidException.class)public ResponseEntity<String> handleValidationExceptions(MethodArgumentNotValidException ex) {StringBuilder errors = new StringBuilder();ex.getBindingResult().getFieldErrors().forEach(error -> errors.append(error.getDefaultMessage()).append("\n"));return ResponseEntity.badRequest().body(errors.toString());}
}

重新测试

重新运行程序测试,并发送请求,得到如下结果:
在这里插入图片描述
可以观察到,这里仅仅是将错误信息以文本形式展示,并没有返回状态码等信息。

返回特定形式的信息

方式一

重写全局异常处理器:

import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.MethodArgumentNotValidException;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;import java.time.LocalDateTime;
import java.util.HashMap;
import java.util.Map;@ControllerAdvice
public class GlobalExceptionHandler {@ExceptionHandler(MethodArgumentNotValidException.class)public ResponseEntity<Object> handleValidationExceptions(MethodArgumentNotValidException ex) {Map<String, Object> body = new HashMap<>();body.put("timestamp", LocalDateTime.now());body.put("status", 400);body.put("error", "Bad Request");StringBuilder errors = new StringBuilder();ex.getBindingResult().getFieldErrors().forEach(error -> errors.append(error.getDefaultMessage()).append(System.lineSeparator()));body.put("message", errors.toString());return ResponseEntity.badRequest().body(body);}
}

测试结果:
在这里插入图片描述

方式二

  1. 定义一个返回结果类型ApiResult
import lombok.Data;
import java.util.List;@Datapublic class ApiResult {// 定义状态码public static final int OK = 200;public static final int ERROR = 500;public static final int Invalid = 400;// 定义返回结果的字段private int code;private String message;private Object data;// 构造器public ApiResult(int code, String message, Object data) {this.code = code;this.message = message;this.data = data;}// 静态方法创建成功的响应public static ApiResult ok(String message, Object data) {return new ApiResult(OK, message, data);}// 静态方法创建错误的响应public static ApiResult error(String message) {return new ApiResult(ERROR, message, null);}public static ApiResult violateConstraint(List<String> violation) {return new ApiResult(Invalid, "参数校验未通过", violation);}
}
  1. 修改全局异常处理器:
import org.springframework.validation.FieldError;
import org.springframework.web.bind.MethodArgumentNotValidException;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseBody;
import java.util.List;
import java.util.stream.Collectors;@ResponseBody
@ControllerAdvice
public class GlobalExceptionHandler {@ExceptionHandler(MethodArgumentNotValidException.class)public ApiResult handleValidationExceptions(MethodArgumentNotValidException ex) {List<String> violations = ex.getBindingResult().getFieldErrors().stream().map(FieldError::getDefaultMessage).collect(Collectors.toList());return ApiResult.violateConstraint(violations);}
}
  1. 修改UserController中注册接口的返回类型:
@RestController
@RequestMapping("/test")
public class UserController {@Autowiredprivate UserService userService;@PostMapping("/register")public ApiResult registerUser(@RequestBody @Valid User user) {userService.save(user);return ApiResult.ok("用户注册成功",user);}
}

测试结果:
在这里插入图片描述

附:常用的注解

注解适用类型说明使用案例
@Null任意类型被注释的元素必须为null@Null(message = "必须为null")
@NotNull任意类型被注释的元素不能为null@NotNull(message = "不能为null")
@NotEmpty字符串、集合、数组被注释的元素不能为 null 也不能为空@NotEmpty(message = "不能为null或者为空")
@NotBlank字符串被注释的字符串不能为 null ,且去除空格后的长度不为 0@NotBlank(message = "name为必传参数")
@Size字符串、集合、数组被注解的元素的大小必须在指定的范围内@Size(min = 5,max = 20,message = "字符长度在 5 -20 之间")
@Min数字被注解的元素必须是一个数字,其值必须大于等于指定的最小值@Min(value = 0,message = "最小金额不能小于 0")
@Max数字被注解的元素必须是一个数字,其值必须小于等于指定的最大值@Max(value = 200,message = "最大金额不能超过 200")
@DecimalMin数字被注解的元素必须是一个数字,其值必须大于等于指定的最小值,可用于浮点数比较@DecimalMin(value = "0.1",message = "该参数不能小于 0.1")
@DecimalMax数字被注解的元素必须是一个数字,其值必须小于等于指定的最大值,可用于浮点数比较@DecimalMax(value = "100.4",message = "该参数不能大于 100.4")
@Digits数字被注解的元素必须是一个数字,且其值必须在指定的范围内@Digits(integer = 3,fraction = 2,message = "该参数整数位数不能超出3位,小数位数不能超过2位")
@Negative数字被注释的元素必须是负数@Negative(message = "必须是负数")
@NegativeOrZero数字被注释的元素必须是负数或 0@NegativeOrZero(message = "必须是负数或者为0")
@Positive数字被注释的元素必须是正数@Positive(message = "必须是正数")
@PositiveOrZero数字被注释的元素必须是正数或0@PositiveOrZero(message = "必须是正数或者为0")
@Pattern字符串被注解的字符串必须符合指定的正则表达式@Pattern(regexp = "^1[3456789]\d{9}$",message = "手机号格式不正确")
@Email字符串被注解的元素必须是一个电子邮件地址@Email(message = "email格式错误")
@Future日期、时间被注解的元素必须是一个将来的日期@Future(message = "预约日期要大于当前日期")
@FutureOrPresent日期、时间被注释的元素必须是现在或者未来的日期@FutureOrPresent(message = "预约日要大于当前日期")
@AssertTrue布尔被注解的元素必须是true@AssertTrue(message = "该参数必须为 true")
@AssertFalse布尔被注解的元素必须是false@AssertFalse(message = "该参数必须为 false")

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

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

相关文章

想知道股指期货和期权有什么不同吗?

市场上目前有中金所的沪深300ETF&#xff0c;中证500和中证1000股指期货&#xff0c;期权市场有上证50ETF&#xff0c;沪深300etf和中证500ETF期权&#xff0c;股指期货和期权在买卖双方的权利义务、风险收益特征、保证金制度、上市合约数量等方面均有较大区别&#xff0c;下文…

每天学点小知识:Windows终端Powershell美化

前言 本章的旨在教会你美化自己的终端&#xff0c;powershell需要以管理员运行 经过我的测试&#xff0c;不同的电脑可能会有不同的报错&#xff0c;具体操作根据官方为主https://ohmyposh.dev/docs 效果展示 Oh My Posh&#xff1a;提供美观的 PowerShell 提示符主题 1.安装…

揭秘CISA:你不知道的信息安全认证,轻松掌握职场先机!

在当今的信息化时代&#xff0c;信息系统的安全和稳定是企业和组织的重要资产。信息系统审计是一项专业的工作&#xff0c;需要具备丰富的知识和经验&#xff0c;以及敏锐的洞察力和判断力。信息系统审计师是信息系统审计领域的专业人士&#xff0c;他们负责对信息系统的设计、…

【OpenGL实践12】关于缓存区Framebuffer的运用

文章目录 一、说明二、帧缓冲区三、创建新的帧缓冲区四、附属装饰4.1 纹理图像4.2 渲染缓冲区对象图像 五、使用帧缓冲区5.1 后期处理5.2 更改代码 六、后期处理效果6.1 色彩处理6.2 模糊6.3 Sobel算子 七、结论练习 一、说明 关于FrameBuffer的使用&#xff0c;是OpenGL的高级…

横截面分位数回归

一、分位数回归简介 分位数回归&#xff08;英语&#xff1a;Quantile regression&#xff09;是回归分析的方法之一。最早由Roger Koenker和Gilbert Bassett于1978年提出。一般地&#xff0c;传统的回归分析研究自变量与因变量的条件期望之间的关系&#xff0c;相应得到的回归…

AI时代的服装设计师--AIGC

AI时代的服装设计师--AIGC AIGCAIGC设计能替代真正的设计师吗森马T恤设计AIGC优势、优化 本文记录于去年参加的一次森马T恤设计活动的感受。 AIGC 可以说&#xff0c;近期以来&#xff0c;随着ChatGPT的不断发展&#xff0c;从ChatGPT-3到ChatGPT-4的飞速发展&#xff0c;AIGC…

Windows和Linux系统部署Docker(2)

目录 一、Linux系统部署docker 前置环境&#xff1a; 1.安装需要的软件包&#xff0c; yum-util 提供yum-config-manager功能 2.添加阿里云 docker-ce 仓库 3.安装docker软件包 4.启动 docker并设置开机自启 5.查看版本&#xff1a; 二、windows系统部署docker 1.查看…

Type ‘null‘ is not assignable to type ‘T‘. - ArkTSCheck

设置泛型将参数配置为 null 时抛出了如下异常: Type null is not assignable to type T. T could be instantiated with an arbitrary type which could be unrelated to null. <ArkTSCheck> 解决办法 在 null 后面添加 ! 即可,以表示该值不会为 null data: T null! 以…

Qt 基于FFmpeg的视频转换器 - 转GIF动图

Qt 基于FFmpeg的视频转换器 - 转GIF动图 引言一、设计思路二、核心源码三、参考链接 引言 gif格式的动图可以通过连续播放一系列图像或视频片段来展示动态效果&#xff0c;使信息更加生动形象&#xff0c;可以很方便的嵌入到网页或者ppt中。上图展示了视频的前几帧转为gif动图的…

基于Paraformer的alpha-token强制对齐

1. 基本原理 CIF 作为Parafoemr的核心模块&#xff0c;用于预测字数和生成声学向量&#xff0c;从而实现了单轮非自回归解码。其中字数的预测主要通过encoder输出系数alpha的累计得分&#xff0c;满足通关阈值β1.0即可产生一个token&#xff0c;其中alpha曲线在一定程度上呈现…

CSS:浮动

▐ 文档流&#xff1a; 由于网页默认是一个二维平面&#xff0c;当我们在网页中一行行摆放标签时&#xff0c;块标签会独占一行&#xff0c;行标签则只占自身大小&#xff0c;这种情况下要实现网页布局就很麻烦了&#xff0c;所以我们就需要通过一些方法来改变这种默认的布局方…

centos7离线安装pthon3.8

centos7离线安装pthon3.8 因服务器无外网环境&#xff0c;所以事先需要把所有离线的依赖都准备好。 安装前的准备 先在有外网环境的机器上准备依赖 安装 centos-release-scl 第三方yum源 yum install centos-release-scl安装 yum 依赖下载插件 yum install yum-plugin-do…

GO语言 gin框架 简述

原文地址 基本路由 Go语言中文文档 一、简介 Gin是一个golang的轻量级web框架&#xff0c;性能不错&#xff0c;API友好。 Gin支持Restful风格的API&#xff0c;可以直接从URL路径上接收api参数或者URL参数&#xff0c;也可是使用json或者表单 数据绑定的方式接收参数。 Gin响…

【传知代码】BERT论文解读及情感分类实战-论文复现

文章目录 概述原理介绍BERT模型架构任务1 Masked LM&#xff08;MLM&#xff09;任务2 Next Sentence Prediction (NSP)模型输入下游任务微调GLUE数据集SQuAD v1.1 和 v2.0NER 情感分类实战IMDB影评情感数据集数据集构建模型构建 核心代码超参数设置训练结果注意事项 小结 本文…

AIOps在线评测基准首阶段建设完成,面向社区发布真实运维数据!

本文根据必示科技算法研究员、产品总监聂晓辉博士在2024 CCF国际AIOps挑战赛线下宣讲会上的演讲整理成文。 2024年1月份OpenAIOps社区成立&#xff0c;随着越来越多的社区成员加入&#xff0c;各项工作在有条不紊的推进中。在线评测基准系统&#xff08;AIOps Live Benchmark&a…

积鼎CFDPro水文水动力模型,专为中小流域洪水“四预”研发的流体仿真技术

水动力模型与水文模型是水利工程与水文学研究中不可或缺的两大工具。水动力模型着重于流体运动的动力学机制&#xff0c;通过一系列方程组捕捉水流的时空变化&#xff0c;而概念性水文模型则侧重于流域尺度的水文循环过程&#xff0c;利用物理概念与经验关系进行近似模拟。两者…

Windows系统部署YOLOv5 v6.1版本的训练与推理环境保姆级教程

文章目录 一 概述二 依赖环境(prerequisites)2.1 硬件环境2.2 软件环境 三 环境安装3.1 创建并激活虚拟环境3.2 安装Pytorch与torchvision3.3 校验Pytorch安装3.4 下载 YOLOv5 v6.1 源码3.5 安装 YOLOv5 依赖3.6 下载预训练模型3.7 安装其他依赖3.8 测试环境安装3.9 测试训练流…

jupyter notebook更改位置

1.找到jupyer的配置文件 一般在c盘用户的.jupter文件夹下 2. 用记事本打开这个配置文件&#xff0c;定位到c.NotebookApp.notebook_dir /path_to_your_directory 替换你的位置 3.找到jupyer图标的位置&#xff0c;打开属性 添加要存放的位置在目标文件的末尾&#xff0c;重新…

一个全面了解Xilinx FPGA IP核的窗口:《Xilinx系列FPGA芯片IP核详解》(可下载)

随着摩尔定律的逐渐放缓&#xff0c;传统的芯片设计方法面临着越来越多的挑战。而FPGA以其并行处理能力和可编程性&#xff0c;为解决复杂问题提供了新的途径。它允许设计者在同一个芯片上实现多种不同的功能模块&#xff0c;极大地提高了资源的利用率和系统的综合性能。 FPGA…

HCIA-ARP

ARP的由来 ARP这一种协议它会是在我们HCIA中第一个需要完全掌握的一个协议&#xff0c;不然对于数据通讯来说大家都会一直觉得很绕圈 协议栈&#xff0c;网线&#xff0c;网卡&#xff0c;它们组成了我们最小的数据通信的小脉络注&#xff1a;可以了解ARP攻击&#xff08;冒充访…