自定义时间校验器

时常可能有这样的需求:在请求之前对于请求参数做校验,这样做一方面可以过滤掉一部分无效的请求(请求参数错误),另一方面也可以有效的限制错误请求占用请求时间,减少并发。而且在请求之前做参数校验是很好的,在数据的源头遏制脏数据,会比在代码中,甚至数据库中处理数据要方便和省力很多。

最近在做一个项目需要自定义一个时间校验器做接口参数的时间校验

  1. 需要校验传入的时间
  2. 不能使用自定义的响应来判断程序是否能调通,而要使用http的状态码来判断
  3. 注意时间格式需要从客户的订单数据中捞一下(避免直接使用文档中可能和客户的时间格式不同,前提是我们已经完成了联调和测试)

先看看最终的实现效果

image-20211103160054078

想法1:

校验时间的工具方法即可

想在方法里面拿到请求的参数然后写一个校验的方法做时间参数的校验,这种方法是可以实现对于请求参数做参数校验的,最终根据校验方法的结果自定义响应结果。

但是我们接口已经大致开发好,而且接口文档提供的是使用http的状态码来作为最终的响应,而不是使用自定义的响应。

想法2

使用常见的时间校验器

比如@DatetimeFormat注解来做校验

报错

日期转换异常 JSON parse error: Cannot deserialize value of type java.util.Date from String

在网上搜索很很多处理方式:比如说使用JsonFormat等或者加时区等等的处理方式,发版测试之后还是不生效(这里的不生效指的没有解决异常,仍然报错日期转换异常)

想法3(最终实现)

自定义一个时间校验器的注解来实现自定义的时间校验

自定义注解

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;
/**
 * @Author: leiyu
 * @Date: 2021/11/3
 * @Description:
 */
@Target({ElementType.FIELD, ElementType.PARAMETER})
@Retention(RetentionPolicy.RUNTIME)
@Constraint(validatedBy = DateTimeValidator.class)
public @interface DateTime {

    String message() default "格式错误";

    String[] format() default "yyyy-MM-dd";;

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

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

时间校验器

package com.shuyun.omni.rest;

import javax.validation.ConstraintValidator;
import javax.validation.ConstraintValidatorContext;
import java.text.SimpleDateFormat;
/**
 * @Author: leiyu
 * @Date: 2021/11/3
 * @Description:
 */
public class DateTimeValidator implements ConstraintValidator<DateTime, String> {
   private DateTime dateTime;
   public void initialize(DateTime dateTime) {
      this.dateTime = dateTime;
   }

   public boolean isValid(String value, ConstraintValidatorContext context) {
      // 如果 value 为空则不进行格式验证,为空验证可以使用 @NotBlank @NotNull @NotEmpty 等注解来进行控制,职责分离
      if (value == null) {
         return true;
      }
      String[] format = dateTime.format();
      for (int i = 0; i < format.length; i++) {
         if (value.length() == format[i].length()) {
            SimpleDateFormat simpleDateFormat = new SimpleDateFormat(format[i]);
            try {
               simpleDateFormat.parse(value);
               return true;
            } catch (Exception e) {
               return false;
            }
         }
      }
      return false;
   }
}

最终实现

image-20211103170038616

  1. 可以实现对于时间的格式校验
  2. 可以配合@NotBlank等注解配合使用,比较灵活
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

炒冷饭

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值