使用validator实现枚举类型校验

使用validator实现枚举类型校验

前言: 在前端调用后端接口传递参数的过程中,我们往往需要对前端传递过来的参数进行校验,比如说我们此时需要对用户的状态进行更新,而用户的状态只有正常和已删除,并且是在代码中通过枚举已经定义好的了。此时我们在校验前端传递过来的状态字段的时候,就可以使用validator对状态字段进行校验

1. 解决思路

我们有两种方式可以实现:

  1. 使用validator的@Pattern 注解,此时我们需要将userStatus的类型改为String类型
    @Pattern(regexp = “^[1-2]$”, message = “Status must be 1 or 2”)
  2. 使用自定义枚举校验器

下面我们来重点讲解一下如何基于自定义枚举校验器来实现对枚举类型字段的校验

2. 实现方式

2.1 创建自定义枚举

@Documented
@Target({METHOD, FIELD, ANNOTATION_TYPE, CONSTRUCTOR, PARAMETER, TYPE_USE})
@Retention(RUNTIME)
@Repeatable(EnumValidation.List.class) // 允许在同一元素上多次使用该注解
@Constraint(validatedBy = {EnumValidator.class})
public @interface EnumValidation {
    String message() default "{*.validation.constraint.Enum.message}";

    Class<?>[] groups() default {};

    Class<? extends Payload>[] payload() default {};

    Class<?> clazz();

    String method() default "ordinal";

    @Documented
    @Target({METHOD, FIELD, ANNOTATION_TYPE, CONSTRUCTOR, PARAMETER, TYPE_USE})
    @Retention(RUNTIME)
    @interface List {
        EnumValidation[] value();
    }
}

2.2 创建自定义枚举校验器

/**
 * @desc: 枚举验证器
 * @author: shy
 * @date: 2023/11/13 16:43
 */
public class EnumValidator implements ConstraintValidator<EnumValidation, Object> {

    private EnumValidation annotation;

    @Override
    public void initialize(EnumValidation constraintAnnotation) {
        this.annotation = constraintAnnotation;
    }
    
    @Override
    public boolean isValid(Object value, ConstraintValidatorContext context) {
        if (value == null) {
            return false;
        }
        Object[] objects = annotation.clazz().getEnumConstants();
        try {
            Method method = annotation.clazz().getMethod(annotation.method());
            for (Object o : objects) {
                if (value.equals(method.invoke(o))) {
                    return true;
                }
            }
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
        return false;
    }
}

2.3 用户状态枚举

属性的get方法必须要实现,此处直接使用Lombok

/**
 * @desc: 用户状态枚举
 * @author: shy
 * @date: 2022/2/4 0:36
 */
@Getter
public enum UserStatusEnum {
    正常(1),
    已删除(2);

    final int value;

    UserStatusEnum(int value) {
        this.value = value;
    }
}

2.4 枚举添加

此时我们就可以直接在相应的字段上加上自定义好的注解

@Data
@FieldDefaults(level = AccessLevel.PRIVATE)
@ApiModel(description = "用户更新参数")
public class UserUpdateParam implements Serializable {

    private static final long serialVersionUID = -484458568568755349L;

    @ApiModelProperty(value = "用户id", name = "userId", required = true)
    @NotNull(message = "用户id不能为空")
    Integer userId;

    @ApiModelProperty(value = "用户状态", name = "userStatus", required = true)
    @EnumValidation(clazz = UserStatusEnum.class, method = "getValue", message = "用户状态不合法")
    Integer userStatus;
}

3. 测试

此时我们调用更新接口进行,就可以看到如下结果:
在这里插入图片描述
至此,大功告成!

4. 总结

一开始的时候是想通过@Max和@Min的方式去实现,但是觉着那样的方式不够优雅,而且用户如果新增了别的状态,涉及到状态校验的地方都需要改动,涉及范围比较广,所以想到了这样的方式。

欢迎大家借鉴参考~

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

云流量回溯的重要性和应用

云流量回溯是指利用云计算和相关技术来分析网络流量、数据传输或应用程序操作的过程。这个过程包括了对数据包、通信模式和应用程序性能的审查和跟踪。本文将介绍云流量回溯重要性和应用! 1、网络安全: 云流量回溯是网络安全的重要组成部分。通过监测和回溯网络流量&#xff0c…

ArcGIS实现矢量区域内所有要素的统计计算

1、任务需求&#xff1a;统计全球各国所有一级行政区相关属性的总和。 &#xff08;1&#xff09;有一个全球一级行政区的矢量图&#xff0c;包含以下属性&#xff08;洪灾相关属性 province.shp&#xff09; &#xff08;2&#xff09;需要按照国家来统计各个国家各属性的总值…

探索STM32系列微控制器的特性和性能

STM32系列微控制器是意法半导体&#xff08;STMicroelectronics&#xff09;公司开发的一款强大的嵌入式微控制器系列。该系列微控制器以其丰富的特性和卓越的性能&#xff0c;成为了嵌入式系统开发领域的首选。本文将深入探索STM32系列微控制器的特性和性能&#xff0c;并结合…

【OpenCV(3)】linux arm aarch 是 opencv 交叉编译与使用

文章目录 1、直接找github 别人编译好的2、自主编译参考 3使用CMake检查 参考 1、直接找github 别人编译好的 测试很多&#xff0c;找到一个可用的。 https://github.com/dog-qiuqiu/libopencv 它用了超级模块&#xff01; OpenCV的world模块也称为超级模块&#xff08;supe…

【c++】——类和对象(中)——实现完整的日期类

作者:chlorine 专栏:c专栏 我的花一定会开。 【学习目标】 拷贝复制——赋值运算符重载 目录 &#x1f393;运算符重载(-><...) &#x1f393;日期&天数 &#x1f393;前置和后置重载 我们完成了赋值运算符重载章节的学习&#xff0c;对operator关键字的使用有…

Python爬虫从基础到入门:找数据接口

Python爬虫从基础到入门:找数据接口 1. 怎样判断抓取的数据是动态生成的2. 用requests模块访问,然后用解析模块解析数据3. 总结1. 怎样判断抓取的数据是动态生成的 请参考文章:Python爬虫从基础到入门:认识爬虫 第3点所讲。 这里用我的CSDN个人主页举例。 可以说这部分下的…

分类预测 | MATLAB实现基于Isomap降维算法与改进蜜獾算法IHBA的Adaboost-SVM集成多输入分类预测

分类预测 | MATLAB实现基于Isomap降维算法与改进蜜獾算法IHBA的Adaboost-SVM集成多输入分类预测 目录 分类预测 | MATLAB实现基于Isomap降维算法与改进蜜獾算法IHBA的Adaboost-SVM集成多输入分类预测分类效果基本描述程序设计参考资料 分类效果 基本描述 Isomap-Adaboost-IHBA-…

拆位线段树 E. XOR on Segment

Problem - E - Codeforces 区间求和&#xff0c;区间异或的操作跟线段树的区间求和、区间相见相似&#xff0c;考虑用线段树。 发现数组初始值最多是1e6&#xff0c;有不到25位&#xff0c;可以知道异或最大值是这些位数全是1的情况。 发现可以对每一位进行运算就和。 我们开…

详解IP安全:IPSec协议簇 | AH协议 | ESP协议 | IKE协议

目录 IP安全概述 IPSec协议簇 IPSec的实现方式 AH&#xff08;Authentication Header&#xff0c;认证头&#xff09; ESP&#xff08;Encapsulating Security Payload&#xff0c;封装安全载荷&#xff09; IKE&#xff08;Internet Key Exchange&#xff0c;因特网密钥…

【JUC】三、集合的线程安全

文章目录 1、ArrayList集合线程安全问题分析2、解决方式一&#xff1a;Vector或synchronizedList( )3、解决方式二&#xff1a;CopyOnWriteArrayList 写时复制4、HashSet集合线程不安全的分析与解决5、HashMap集合线程不安全的分析与解决 1、ArrayList集合线程安全问题分析 对…

Vue学习笔记

Vue学习笔记 数据绑定脚手架Vue CLI 组件组件化开发需要安装的插件自定义组件定义自己的组件使用自定义的组件 普通组件--局部注册普通组件--全局注册普通组件的局部注册和全局注册的区别第三方组件Element-uicomputed 计算属性修改计算属性 watch 侦听器延时器防抖watch 的完整…

sass 生成辅助色

背景 一个按钮往往有 4 个状态。 默认状态hover鼠标按下禁用状态 为了表示这 4 个状态&#xff0c;需要设置 4 个颜色来提示用户。 按钮类型一般有 5 个&#xff1a; 以 primary 类型按钮为例&#xff0c;设置它不同状态下的颜色&#xff1a; <button class"btn…

lc307.区域和检索 - 数组可修改

暴力解法 创建方法&#xff0c;通过switch-case判断所需要调用的方法。 public class RegionsAndSertches {public static void main(String[] args) {String[] str new String[]{"NumArray", "sumRange", "update", "sumRange"};i…

互联网Java工程师面试题·微服务篇·第二弹

目录 18、什么是 Spring 引导的执行器&#xff1f; 19、什么是 Spring Cloud&#xff1f; 20、Spring Cloud 解决了哪些问题&#xff1f; 21、在 Spring MVC 应用程序中使用 WebMvcTest 注释有什么用处&#xff1f; 22、你能否给出关于休息和微服务的要点&#xff1f; 23、…

c语言-assert(断言)的笔记

一、assert(断言)简介 assert的功能&#xff0c;条件为真&#xff0c;程序继续执行&#xff1b;如果断言为假&#xff08;false&#xff09;&#xff0c;则程序终止。 assert是个宏定义&#xff01; 头文件&#xff1a; #include <assert.h> 原型&#xff1a; void asser…

nacos适配达梦数据库

一、下载源码 源码我直接下载gitee上nacos2.2.3的&#xff0c;具体链接&#xff1a;https://gitee.com/mirrors/Nacos/tree/2.2.3&#xff0c;具体如下图&#xff1a; 二、集成达梦数据库驱动 解压源码包&#xff0c;用idea打开源码&#xff0c;等idea和maven编译完成&#xff…

HarmonyOS开发(三):ArkTS基础

1、ArkTS演进 Mozilla创建了JS ---> Microsoft创建了TS ----> Huawei进一步推出ArkTS 从最初的基础逻辑交互&#xff08;JS&#xff09;,到具备类型系统的高效工程开发&#xff08;TS&#xff09;,再到融合声明式UI、多维状态管理等丰富的应用开发能力&…

SDL2 播放视频数据(YUV420P)

1.简介 这里以常用的视频原始数据YUV420P为例&#xff0c;展示视频的播放。 SDL播放视频的流程如下&#xff1a; 初始化SDL&#xff1a;SDL_Init();创建窗口&#xff1a;SDL_CreateWindow();创建渲染器&#xff1a;SDL_CreateRenderer();创建纹理&#xff1a;SDL_CreateText…

ESP32 Arduino引脚分配参考:您应该使用哪些 GPIO 引脚?

ESP32 芯片有 48 个引脚&#xff0c;具有多种功能。并非所有 ESP32 开发板中的所有引脚都暴露出来&#xff0c;有些引脚无法使用。 关于如何使用 ESP32 GPIO 有很多问题。您应该使用什么引脚&#xff1f;您应该避免在项目中使用哪些引脚&#xff1f;这篇文章旨在成为 ESP32 GP…

Spark3.0中的AOE、DPP和Hint增强

1 Spark3.0 AQE Spark 在 3.0 版本推出了 AQE&#xff08;Adaptive Query Execution&#xff09;&#xff0c;即自适应查询执行。AQE 是 Spark SQL 的一种动态优化机制&#xff0c;在运行时&#xff0c;每当 Shuffle Map 阶段执行完毕&#xff0c;AQE 都会结合这个阶段的统计信…