简单介绍下 Java 中的 @Validated 和 @Valid 注解的区别?

devtools/2024/11/14 19:23:16/

文章目录

      • @Valid:专注单个对象的深度验证
        • 适用场景
        • 使用示例
        • 小结
      • @Validated:聚焦接口分组的批量验证
        • 适用场景
        • 使用示例
        • 小结
      • 主要区别总结
      • 如何选择?
      • 总结
      • 推荐阅读文章

Java 开发中,为了确保输入数据符合我们的要求,少不了数据验证这一步。 @Valid@Validated 是两个常见的验证注解,它们在 Spring 中常常出现,虽然名字差不多,但作用和使用场景却不太一样。

今天,我们就来聊聊 @Valid@Validated 的区别,看它们如何在验证世界里各司其职,搭配使用!


@Valid:专注单个对象的深度验证

@ValidJava 中的标准验证注解,适用于单个对象的验证。它的职责很清晰——递归地验证这个对象,尤其适用于嵌套对象的场景。

比如,你的表单里有个 User 对象,User 里还有 Address 对象,那么在验证 User 时,如果用了 @Valid,它会一层层地深入到 Address,对所有字段进行完整验证。

适用场景

@Valid 更适合在字段上进行深层次的验证,比如:

  • 方法参数:在方法参数前标注 @Valid,让 Spring 验证参数。
  • 嵌套对象:在对象内部的字段上使用 @Valid,确保递归验证。
使用示例
public class User {@NotNullprivate String name;@Valid // 在嵌套对象 Address 上使用 @Validprivate Address address;
}public class Address {@NotBlankprivate String city;
}

在这个例子中,@Valid 会确保 User 对象的 address 字段也被验证。因此,如果 addresscity 是空字符串,也会报错。

小结

@Valid 是一种“全家桶”式的验证器,用来递归检查整个对象树的各个字段是否符合要求。


@Validated:聚焦接口分组的批量验证

@Validated 是 Spring 特有的验证注解,和 @Valid 不同的是,它的主要优势在于支持验证分组。分组验证的概念很简单:比如,我们在用户注册时要验证的内容和在用户更新资料时可能不同。@Validated 就允许你给验证分组,灵活地控制哪些验证规则在何时触发。

适用场景
  • 分组验证:需要在不同情况下使用不同的验证规则时,@Validated 是非常合适的选择。
使用示例

假设我们有两个验证场景,一个是 AddGroup(新增用户时的验证),一个是 UpdateGroup(更新用户时的验证),可以这样做:

public class User {@NotNull(groups = AddGroup.class)private String name;@NotBlank(groups = UpdateGroup.class)private String email;
}public interface AddGroup {}
public interface UpdateGroup {}

在控制器方法中,指定使用哪个分组:

@PostMapping("/addUser")
public void addUser(@Validated(AddGroup.class) @RequestBody User user) {// 仅验证 AddGroup 分组
}@PutMapping("/updateUser")
public void updateUser(@Validated(UpdateGroup.class) @RequestBody User user) {// 仅验证 UpdateGroup 分组
}

这样,通过 @Validated 注解和分组,你可以在不同操作中有选择地应用不同的验证逻辑。

小结

@Validated 是一位“分组专家”,适合复杂场景下的批量验证。


主要区别总结

注解验证对象支持分组验证适用场景
@Valid单个对象,递归验证深度验证嵌套对象
@Validated批量验证,可以选择性验证在不同业务场景下应用不同验证逻辑

如何选择?

  • 需要递归验证单个对象的各个字段(尤其是嵌套的复杂对象):用 @Valid
  • 需要在不同操作中选择性验证字段(比如新增和更新的验证规则不同):用 @Validated,并分配分组。

总结

  • @Valid 是“单体专家”,适合一层层深入对象结构,逐个检查字段。
  • @Validated 是“分组大拿”,让你灵活控制不同场景下的验证要求。

理解这两个注解的分工后,就可以让你的 Java 应用在数据验证上更严谨、更灵活啦!

推荐阅读文章

  • 由 Spring 静态注入引发的一个线上T0级别事故(真的以后得避坑)
  • 如何理解 HTTP 是无状态的,以及它与 Cookie 和 Session 之间的联系
  • HTTP、HTTPS、Cookie 和 Session 之间的关系
  • 什么是 Cookie?简单介绍与使用方法
  • 什么是 Session?如何应用?
  • 使用 Spring 框架构建 MVC 应用程序:初学者教程
  • 有缺陷的 Java 代码:Java 开发人员最常犯的 10 大错误
  • 如何理解应用 Java 多线程与并发编程?
  • 把握Java泛型的艺术:协变、逆变与不可变性一网打尽
  • Java Spring 中常用的 @PostConstruct 注解使用总结
  • 如何理解线程安全这个概念?
  • 理解 Java 桥接方法
  • Spring 整合嵌入式 Tomcat 容器
  • Tomcat 如何加载 SpringMVC 组件
  • “在什么情况下类需要实现 Serializable,什么情况下又不需要(一)?”
  • “避免序列化灾难:掌握实现 Serializable 的真相!(二)”
  • 如何自定义一个自己的 Spring Boot Starter 组件(从入门到实践)
  • 解密 Redis:如何通过 IO 多路复用征服高并发挑战!
  • 线程 vs 虚拟线程:深入理解及区别
  • 深度解读 JDK 8、JDK 11、JDK 17 和 JDK 21 的区别
  • 10大程序员提升代码优雅度的必杀技,瞬间让你成为团队宠儿!
  • “打破重复代码的魔咒:使用 Function 接口在 Java 8 中实现优雅重构!”
  • Java 中消除 If-else 技巧总结
  • 线程池的核心参数配置(仅供参考)
  • 【人工智能】聊聊Transformer,深度学习的一股清流(13)
  • Java 枚举的几个常用技巧,你可以试着用用

http://www.ppmy.cn/devtools/133249.html

相关文章

libgdiplus在MacOS M1上问题:Unable to load shared library ‘libgdiplus‘

libgdiplus在MacOS M1上问题:Unable to load shared library libgdiplus 问题解决步骤1步骤2 问题 在mac上的pycharm中执行下面的代码时出现下面的错误 slide.get_thumbnail( RuntimeError: Proxy error(TypeInitializationException): The type initializer for…

IntelliJ IDEA的快捷键

IntelliJ IDEA 是一个非常强大的集成开发环境,它提供了大量的快捷键来加速开发者的日常工作。这里为您整理了一份 IntelliJ IDEA 的快捷键大全,包含了编辑、导航、重构、运行等多个方面的快捷键。请注意,这些快捷键是基于 Windows 版本的 Int…

shell--常用命令

命令执行失败之后的操作 teee --version || { echo "tee command not found"; exit 1; } /dev/null /dev/null 对应的是一个空设备文件,任何写入这个文件的数据都将立即被销毁,而不是写到磁盘上。 if dpkg -s software-properties-common &g…

【Vue】-组件开发-一个树组件

我们来自己搞一个树组件 1. 创建 Vue 项目 如果你还没有创建 Vue 项目,可以使用 Vue CLI 快速创建: vue create my-tree-component cd my-tree-component2. 安装依赖 确保安装了 Vue Router 和 Vuex(如果需要状态管理)&#x…

Java 中的 transient 关键字:深入解析与实战

在 Java 编程中,transient 关键字是一个非常有用的工具,尤其是在处理对象序列化时。尽管 transient 关键字在日常开发中可能不常被使用,但了解它的作用和使用场景对于提升代码的安全性和性能至关重要。本文将深入探讨 transient 关键字的作用…

【网络-交换机】生成树协议、环路检测

路由优先级 路由优先级决定了在多种可达的路由类型中,哪种路由将被用来转发数据包。路由优先级值越低,对应路由的优先级越高,优先级值255表示对应的路由不可达。一般情况下,静态路由的优先级为1,OSPF路由优先级为110&a…

gan的所有种类,人工智能 机器学习,gan的所有算法

参考最全汇总GAN网络及其各种变体(附论文及代码实现)_gan网络代码-CSDN博客 这是我找到的关于您提问的答案: 1. **GAN类型**: Auxiliary Classifier GAN **参考论文**: 《Conditional Image Synthesis With Auxiliary Classifier GANs》 **代码地址**: …

基于Redis缓存机制实现高并发接口调试

创建接口 这里使用的是阿里云提供的接口服务直接做的测试,接口地址 curl http://localhost:8080/initData?tokenAppWithRedis 这里主要通过参数cacheFirstfalse和true来区分是否走缓存,正常的业务机制可能是通过后台代码逻辑自行控制的,这…