通过拦截器和注解方式,实现HttpServletRequest方式参数校验

本例基于springboot,HttpServletRequest传参方式作参数校验,通过自定义拦截器获取HttpServletRequest请求,在拦截器里根据自定义注解做参数校验。代码如下:

首先是两个用于指定校验类型的注解:
@CheckParams和@CheckRule,@CheckParams中有一个CheckRule[]数组,用于实现可指定多个参数的校验规则:

@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface CheckParams {

    CheckRule[] rules();
}

@CheckRule中用于指定校验细则:

@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface CheckRule {
    String attrName();
    boolean notNull() default false;
    String message() default "参数未通过校验";
    CheckType type();
    String value() default "";
}

attrName用于指定要校验参数名,用于request取参数。
message用于传递校验失败时,需要传递的错误信息。
type用于指定校验的类型,根据自己的业务指定,如电话号码,邮箱等
value用于指定特殊校验时的值域,如不大于多少,不小于多少等。

CheckType 是根据自己需要校验的类型,列举的枚举值,本例中:

public enum  CheckType {
    //整数最大值
    INT_MAX,
    //整数最小值
    INT_MIN,
    //正则匹配
    REGULAR_MATCH,
    //邮箱
    EMAIL,
    //电话号码
    PHONE;
}

然后是实际用于校验的工具代码:

public class ParamCheckUtil {

    private static final String EMAIL_REGEX = "^([\\w-\\.]+)@((\\[[0-9]{1,3}\\.[0-9]{1,3}\\.[0-9]{1,3}\\.)|(([\\w-]+\\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})(\\]?)$";

    private static final String PHONE_REGEX = "^((13[0-9])|(15[^4,\\D])|(18[0,5-9]))\\d{8}$";


    public static boolean verifyParam(Object verityVaule, boolean notNull, CheckType type, String value) {
        if (null == verityVaule) {
            return !notNull;
        }
        switch(type) {
            case INT_MAX:
                return verifyIntMax(verityVaule, value);
            case INT_MIN:
                return verifyIntMin(verityVaule, value);
            case EMAIL:
                return verifyByRegex(verityVaule, EMAIL_REGEX);
            case PHONE:
                return verifyByRegex(verityVaule, PHONE_REGEX);
            case REGULAR_MATCH:
                return verifyByRegex(verityVaule, value);
            default:
                return false;
        }
    }

    public static void main(String args[]) {
        String e1 = "dfasfdasfasd";
        String e2 = "4329438@qq.com";
        String e3 = "sdfsdfsdf@sdf.sdf";
        System.out.println(verifyByRegex(e1, EMAIL_REGEX));
        System.out.println(verifyByRegex(e2, EMAIL_REGEX));
        System.out.println(verifyByRegex(e3, EMAIL_REGEX));


        String p1 = "dfjasodfjo23";
        String p2 = "3423432";
        String p3 = "13545676789";
        String p4 = "34543454332";
        System.out.println(verifyByRegex(p1, PHONE_REGEX));
        System.out.println(verifyByRegex(p2, PHONE_REGEX));
        System.out.println(verifyByRegex(p3, PHONE_REGEX));
        System.out.println(verifyByRegex(p4, PHONE_REGEX));


    }

    public static boolean verifyByRegex(Object verityValue, String regex) {
        return Pattern.matches(regex,verityValue.toString());
    }

    public static boolean verifyIntMax(Object verityValue, String value) {
        return Integer.parseInt(verityValue.toString()) <= Integer.parseInt(value);
    }

    public static boolean verifyIntMin(Object verityValue, String value) {
        return Integer.parseInt(verityValue.toString()) >= Integer.parseInt(value);
    }
}

一切准备就绪,然后就是自定义拦截器和加上拦截器了。
拦截器:

public class ParamCheckInterceptor implements HandlerInterceptor {

    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        if (handler instanceof HandlerMethod) {
            HandlerMethod handlerMethod = (HandlerMethod) handler;
            Method method = handlerMethod.getMethod();
            CheckParams checkParams = method.getAnnotation(CheckParams.class);
            if(checkParams == null || StringUtils.isEmpty(checkParams.rules())) {
                return true;
            }
            for (CheckRule rule: checkParams.rules()) {
                //todo (request.getAttribute(rule.attrName()) 改为实际取值
                if (!ParamCheckUtil.verifyParam(request.getAttribute(rule.attrName()), rule.notNull(), rule.type(), rule.value())) {
                    //todo 抛出异常更换为项目所需业务异常
                    throw new Exception();
                }
            }
        }

        return true;
    }
}

通过实现HandlerInterceptor 定义自己的拦截器,本例中拦截器重载preHandle方法即可,通过CheckParams checkParams = method.getAnnotation(CheckParams.class);可拿到本调用接口是否增加我们自己的注解,需要作参数校验, 然后根据rule.attrName()拿到我们指定的需要校验的参数名,再到request里去获取,最后根据注解类型进行校验。这里抛出的异常可使用我们@CheckRule中message中的信息做异常信息的传递。

最后,通过@Configuration注解启用我们的拦截器:

@Configuration
public class MyConfig implements WebMvcConfigurer {

    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(new ParamCheckInterceptor());
    }
}
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
在Java中,拦截器(Interceptor)是一种常见的设计模式,用于在方法调用之前或之后添加额外的逻辑处理。在Web开发中,拦截器常用于处理请求、验证用户身份、记录日志等操作。下面是一个简单的示例,演示如何实现一个拦截器。 首先,创建一个拦截器类,实现Spring框架的`HandlerInterceptor`接口。该接口定义了三个方法,分别对应请求处理前、请求处理后和请求完成后的操作。 ```java import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import org.springframework.web.servlet.HandlerInterceptor; import org.springframework.web.servlet.ModelAndView; public class MyInterceptor implements HandlerInterceptor { @Override public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception { // 在请求处理前执行的逻辑 // 返回true表示继续执行后续操作,返回false表示中断请求处理 return true; } @Override public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception { // 在请求处理后执行的逻辑 } @Override public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception { // 在请求完成后执行的逻辑 } } ``` 接下来,配置拦截器类,让它生效。可以通过Spring配置文件或注解方式进行配置。 通过Spring配置文件配置拦截器: ```xml <!-- 配置拦截器 --> <mvc:interceptors> <mvc:interceptor> <mvc:mapping path="/**"/> <!-- 拦截所有请求 --> <bean class="com.example.MyInterceptor"/> </mvc:interceptor> </mvc:interceptors> ``` 通过注解配置拦截器: ```java import org.springframework.context.annotation.Configuration; import org.springframework.web.servlet.config.annotation.InterceptorRegistry; import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; @Configuration public class WebConfig implements WebMvcConfigurer { @Override public void addInterceptors(InterceptorRegistry registry) { registry.addInterceptor(new MyInterceptor()).addPathPatterns("/**"); // 拦截所有请求 } } ``` 以上示例中的`com.example.MyInterceptor`是自定义的拦截器类,你可以根据实际需求来编写自己的拦截器逻辑。在`preHandle`方法中可以进行请求的预处理,如验证用户身份、权限校验等;在`postHandle`方法中可以对响应进行处理;在`afterCompletion`方法中可以进行一些清理工作。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值