• 自定义注解实现验证信息的功能


    自定义注解实现验证逻辑

    • 导包
            <!-- hibernate 验证框架 -->
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-validation</artifactId>
            </dependency>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 定义BO对象,前端传来的业务对象,对象中的属性需要校验
    package com.imooc.boapi;
    
    //import com.imooc.annotationcustom.VlogId;
    import com.imooc.annotationcustom.VlogId;
    import lombok.AllArgsConstructor;
    import lombok.Data;
    import lombok.NoArgsConstructor;
    import lombok.ToString;
    
    @Data
    @AllArgsConstructor
    @NoArgsConstructor
    @ToString
    public class VlogBOApi {
        private String id;
       @VlogId(message = "用户不存在,禁止插入视频")
        private String vlogerId;
        private String url;
        private String cover;
        private String title;
        private Integer width;
        private Integer height;
        private Integer likeCounts;
        private Integer commentsCounts;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 定义一个校验注解
    package com.imooc.annotationcustom;
    
    
    
    
    import javax.validation.Constraint;
    import javax.validation.Payload;
    import java.lang.annotation.ElementType;
    import java.lang.annotation.Retention;
    import java.lang.annotation.RetentionPolicy;
    import java.lang.annotation.Target;
    
    @Target({ ElementType.FIELD})
    @Retention(RetentionPolicy.RUNTIME)
    @Constraint(validatedBy = VlogIdValidator.class) //校验的逻辑处理类
    public @interface VlogId {
        String message();
    
        /**
         * 将validator进行分类,不同的类group中会执行不同的validator操作
         *
         * @return validator的分类类型
         */
        Class<?>[] groups() default {};
    
        /**
         * 主要是针对bean,很少使用
         *
         * @return 负载
         */
        Class<? extends Payload>[] payload() default {};
    }
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 同时需要一个校验类,实现一个注解检验的逻辑
    package com.imooc.annotationcustom;
    
    import com.imooc.mapper.UsersMapper;
    import com.imooc.pojo.Users;
    import lombok.extern.slf4j.Slf4j;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.stereotype.Component;
    
    import javax.validation.ConstraintValidator;
    import javax.validation.ConstraintValidatorContext;
    
    @Slf4j
    @Component
    public class VlogIdValidator implements ConstraintValidator<VlogId, String> {
    
    
        @Autowired
        UsersMapper usersMapper;
    
        @Override
        public void initialize(VlogId constraintAnnotation) {
            log.info("注解逻辑初始化");
        }
    
        @Override
        public boolean isValid(String s, ConstraintValidatorContext constraintValidatorContext) {
            Users user = new Users();
            user.setId(s);
            Users reslut = usersMapper.selectByPrimaryKey(user);
            System.out.println("注解拦截生效+package com.imooc.annotationcustom;");
            if (reslut == null) {
                return false;
            } else {
                return true;
            }
        }
    
    }
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 业务代码
        @PostMapping("publish")
        public GraceJSONResult publish(@Valid @RequestBody VlogBOApi vlogBO) {
    
    //        vlogService.createVlog(vlogBO);
            return GraceJSONResult.ok();
        }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 校验失败异常,定义一个全局异常捕获,将这个错误返回给前端
        @ExceptionHandler(MethodArgumentNotValidException.class)
        @ResponseBody
        public GraceJSONResult returnMethodArgumentNotValid(MethodArgumentNotValidException e) {
            BindingResult result = e.getBindingResult();
            Map<String, String> map = getErrors(result);
            return GraceJSONResult.errorMap(map);
        }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7

    自定义注解来简化开发

    目的:做一个点赞次数拦截的功能。过程:需要拦截以后自行确定多少时间内的点赞次数

    • 定义注解:
    package com.imooc.annotationcustom;
    
    
    import java.lang.annotation.*;
    
    
    @Inherited
    @Documented
    @Target({ElementType.FIELD, ElementType.TYPE, ElementType.METHOD})
    @Retention(RetentionPolicy.RUNTIME)
    public @interface RequestLimit {
        /**
         * 时间内 秒为单位
         * @return
         */
        int second() default 10;
    
        /***
         * 允许访问次数
         * @return
         */
    
        int maxCount() default 5;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 拦截器代码,这里需要获取接口上的自定义注解handlerMethod.getMethodAnnotation
            if (handler instanceof HandlerMethod) {
                HandlerMethod handlerMethod =  (HandlerMethod) handler;
                //获取RequestLimit注解
                RequestLimit requestLimit = handlerMethod.getMethodAnnotation(RequestLimit.class);
                if (null == requestLimit) {
                    System.out.println("没有获取到注解");
                    return true; //每加注解说明没有限制,多少次都ok
                }
                //限制的时间范围
                int seconds = requestLimit.second();
                //限制时间内的最大次数
                int maxCount = requestLimit.maxCount();
                //获取用户ip
                String userIp = IPUtil.getRequestIp(request);
                //判断redis中是否有ip
                boolean keyIsExist = redis.keyIsExist(LIKE_VLOG_OPERATE_COUNT + ":" + userIp);
    
                //如果没有这个键,说明当前用户在20s内没有点过赞,因为这个拦截器就是拦截点赞的后端接口,所以如果没有这个键就设置一个键
                if (keyIsExist == false) {
                    redis.set(LIKE_VLOG_OPERATE_COUNT + ":" + userIp, "0", seconds);
                    System.out.println("ok");
                    return  true;
                }
                // 返回true,就要判断这个键对应的值的个数
                String res = redis.get(LIKE_VLOG_OPERATE_COUNT + ":" + userIp);
                if (Integer.valueOf(res) >= maxCount) {
                    GraceException.display(ResponseStatusEnum.LIKE_VLOG_WAIT_ERROR);
                    return false;
                }
            }
    
    
    
    
    
            return true;
        }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 业务代码
        @PostMapping("like")
        //TODO: 这里需要调试
        @RequestLimit(maxCount = 3, second = 60)
        public GraceJSONResult like(@RequestParam String userId,
                                    @RequestParam String vlogerId,
                                    @RequestParam String vlogId,
                                    HttpServletRequest request) {
            vlogService.userLikeVlog(userId, vlogId);
            redis.increment(REDIS_VLOGER_BE_LIKED_COUNTS + ":" + vlogerId, 1);
            redis.increment(REDIS_VLOG_BE_LIKED_COUNTS + ":" + vlogId, 1);
    
            redis.set(REDIS_USER_LIKE_VLOG + ":" + userId + ":" + vlogId, "1");
    
            //------------------------------------------//
            //新增功能,限制点赞次数,
            String userIp = IPUtil.getRequestIp(request);
            redis.increment(LIKE_VLOG_OPERATE_COUNT + ":" + userIp,1);
            //-------------------------------------------//
    
    
            return GraceJSONResult.ok();
        }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
  • 相关阅读:
    程序员必须掌握的算法
    Java的构造器
    Linux下Minio分布式存储安装配置(图文详细)
    医疗设备远程监控 5G千兆工业网关智慧医疗
    【Quark RISC-V】流水线CPU设计(4)数据冒险的处理(主要解决方案:流水线暂停、数据转发、乱序执行)
    公网集群对讲+GPS可视追踪|助力物流行业智能化管理调度
    基于全志T133-s3(Tina Linux)移植wifi(rtl8723d)驱动
    Java学习 10.Java-类和对象
    【记事本 】dom操作的类型
    MATLAB|热力日历图
  • 原文地址:https://blog.csdn.net/weixin_42595206/article/details/125531019