解决springboot静态内部类非空校验无效的问题

日常项目中,偶尔会使用到静态内部类。平时对字段做非空校验时,一般会使用javax的注解,如:

java 复制代码
@NotNull(message = "xxx")

如何对静态内部类中的字段做非空校验呢?我是这样写的:

java 复制代码
package cn.uni.boot.module.business.controller.app.finance.verification.vo;

import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;

import javax.validation.Valid;
import javax.validation.constraints.NotBlank;
import javax.validation.constraints.NotNull;

@Data
public class AppVerificationSubmitReqVo {

		// ...

    @Schema(description = "选择商品")
    @NotNull(message = "商品不能为空")
    private ProductInfo product;

        @Data
 		@Valid
    public static class ProductInfo{

        @Schema(description = "xx商品id")
        @NotNull(message = "xx商品id不能为空")
        private Long bankProductId;

        @Schema(description = "xx商品id")
        private Long cProductId;

    }

}

然后发现实际运行时,静态内部类中的字段并没有被成功校验,如'bankProductId'为null时依然可以通过。

查阅相关资料,发现:

@Valid 是用于「触发级联校验」的注解,它必须加在引用嵌套对象的字段上,而不是加在类定义上。

Bean Validation(如 Hibernate Validator)不会读取目标类上的 @Valid 注解来决定是否校验它 ------ 它只看父对象中引用该对象的字段是否标注了 @Valid。

可以把 @Valid 想象成一个"检查许可":

控制器说:"我要校验 AppVerificationSubmitReqVo。"

校验器检查它的字段:

codeId → 有 @NotNull → 检查。

product → 是一个对象 → 看看这个字段有没有 @Valid?

有 → 好,进去检查 ProductInfo 里面的约束。

没有 → 跳过,不管里面写了什么 @NotNull。

所以,@Valid 必须写在字段上,这是规范,不是可选项。

纠正:

java 复制代码
    @Valid // 改到这里
    @Schema(description = "选择商品")
    @NotNull(message = "商品不能为空")
    private ProductInfo product;

    @Data
    public static class ProductInfo{

        @Schema(description = "xxx商品id")
        @NotNull(message = "xxx商品id不能为空")
        private Long bankProductId;

        @Schema(description = "xxx商品id")
        private Long cProductId;

    }
相关推荐
上下求索,莫负韶华9 分钟前
笔记-数据库事务和java事务和切面
java·数据库·笔记
@小匠16 分钟前
Spring Boot Nacos绑定 Map 时中文 key 导致启动失败:一次从复现到源码的排查实录
java·开发语言·前端
Knight_AL17 分钟前
Lombok @Builder 踩坑:build() 前后对象类型不一样
android·java·开发语言
SamChan9040 分钟前
PDF翻译中的并发控制:用Semaphore防止API限流与资源耗尽
java·jvm·pdf
大黄说说1 小时前
Java 与 Kotlin 混合开发避坑指南:老项目平滑迁移 Kotlin 实操手册
java·开发语言·kotlin
郝学胜_神的一滴1 小时前
C++20 高级编程 001:从极简HelloWorld到现代类型体系全梳理
c++·后端
卷无止境1 小时前
FastAPI中间件全解析:请求处理链条上的隐形关卡
后端·python·fastapi
badhope1 小时前
MCP协议:号称要统一AI工具调用,但大多数人连第一步都走不对
后端·架构
用户3126874877201 小时前
接口太慢?Spring Boot 缓存体系 @Cacheable 全链路拆解
spring boot
思考着亮2 小时前
2. Redis 缓存实战
后端