SpringMVC中的JSR303与拦截器的使用

这篇具有很好参考价值的文章主要介绍了SpringMVC中的JSR303与拦截器的使用。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

一,JSR303的概念

     JSR303是Java中的一个标准,用于验证和校验JavaBean对象的属性的合法性。它提供了一组用于定义验证规则的注解,如@NotNull、@Min、@Max等。在Spring MVC中,可以使用JSR303注解对请求参数进行校验。

1.2 为什么要使用JSR303?(更加理解)

前端不是已经校验过数据了吗?为什么我们还要做校验呢,直接用不就好了?草率了,假如说前端代码校验没写好又或者是对于会一点编程的人来说,直接绕过前端发请求(通过类似Postman这样的测试工具进行非常数据请求),把一些错误的参数传过来,你后端代码不就危险了嘛

所以我们一般都是前端一套校验,后端在一套校验,这样安全性就能够大大得到提升了。

1.3 常用的注解

在上面JSR303的概念中也指到了一些注解,以下是注解的详细概述
注解 说明
@Null 用于验证对象为null
@NotNull 用于对象不能为null,无法查检长度为0的字符串
@NotBlank 只用于String类型上,不能为null且trim()之后的size>0
@NotEmpty 用于集合类、String类不能为null,且size>0。但是带有空格的字符串校验不出来
@Size 用于对象(Array,Collection,Map,String)长度是否在给定的范围之内
@Length 用于String对象的大小必须在指定的范围内
@Pattern 用于String对象是否符合正则表达式的规则
@Email 用于String对象是否符合邮箱格式
@Min 用于Number和String对象是否大等于指定的值
@Max 用于Number和String对象是否小等于指定的值
@AssertTrue 用于Boolean对象是否为true
@AssertFalse 用于Boolean对象是否为false

1.4 @Validated与@Valid区别

@Validated:

  • Spring提供的

  • 支持分组校验

  • 可以用在类型、方法和方法参数上。但是不能用在成员属性(字段)上

  • 由于无法加在成员属性(字段)上,所以无法单独完成级联校验,需要配合@Valid

@Valid:

  • JDK提供的(标准JSR-303规范)

  • 不支持分组校验

  • 可以用在方法、构造函数、方法参数和成员属性(字段)上

  • 可以加在成员属性(字段)上,能够独自完成级联校验

 二,JSR303使用

2.1 导入pom.xml依赖

<!-- JSR303 -->
<hibernate.validator.version>6.0.7.Final</hibernate.validator.version>
 
<!-- JSR303 -->
<dependency>
    <groupId>org.hibernate</groupId>
    <artifactId>hibernate-validator</artifactId>
    <version>${hibernate.validator.version}</version>
</dependency>

2.2 配置校验规则

package com.Bingzy.model;

import lombok.ToString;
import org.hibernate.validator.constraints.NotBlank;

@ToString
public class Tbook {

    @ToString
    public class Clazz {
        @NotNull(message = "书籍编号不能为空")
        protected Integer bid;

        @NotBlank(message = "书籍名不能为空")
        protected String bname;

        @NotBlank(message = "书籍价格不能为空")
        protected Float price;


        public Clazz(String bid, String bname, Float price) {
            this.bid = bid;
            this.bname = bname;
            this.price = price;
        }

        public String getBid() {
            return bid;
        }

        public void setBid(String bid) {
            this.bid = bid;
        }

        public String getBname() {
            return bname;
        }

        public void setBname(String bname) {
            this.bname = bname;
        }

        public Float getPrice() {
            return price;
        }

        public void setPrice(Float price) {
            this.price = price;
        }

        @Override
        public String toString() {
            return "Clazz{" +
                    "bid='" + bid + '\'' +
                    ", bname='" + bname + '\'' +
                    ", price=" + price +
                    '}';
        }
    }



}

2.3 入门案例

在请求处理方法中,使用@Validated或@Valid注解要验证的对象,并根据BindingResult判断校验是否通过。

   //    给数据添加服务端校验
    @RequestMapping("/valiAdd")
    public String valiAdd(@Validated Tbook tbook,
                          BindingResult result,
                          HttpServletRequest req){
//        如果服务端验证不通过,有错误
        if(result.hasErrors()){
//            服务端验证了实体类的多个属性,多个属性都没有验证通过
            List<FieldError> fieldErrors = result.getFieldErrors();
            Map<String,Object> map = new HashMap<>();
            for (FieldError fieldError : fieldErrors) {
//                将多个属性的验证失败信息输送到控制台
                System.out.println(fieldError.getField() + ":" + fieldError.getDefaultMessage());
                map.put(fieldError.getField(),fieldError.getDefaultMessage());
            }
            req.setAttribute("errorMap",map);
        }else {
            this.tbookBiz.insertSelective(tbook);
            return "redirect:list";
        }
        return "book/edit";
    }

edit.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>博客的编辑界面</title>
</head>
<body>
<center>
    编辑界面
    <form action="${pageContext.request.contextPath }/${empty b ? 'book/valiAdd' : 'book/edit'}" method="post"><br>
        书籍id:<input type="text" name="bid" value="${b.bid }"><span style="color: red">${errorMap.bid}</span><br>
        书籍名称:<input type="text" name="bname" value="${b.bname }"><span style="color: red">${errorMap.bname}</span><br>
        书籍价格:<input type="text" name="price" value="${b.price }"><span style="color: red">${errorMap.price}</span><br>
        <input type="submit">
    </form>
</center>
</body>
</html>

运行结果:

点击新增或修改,进入页面后点击提交显示相对应的提示语句 

SpringMVC中的JSR303与拦截器的使用,状态模式,mybatis,开发语言,java,intellij-idea,spring

 三,拦截器

3.1 什么是拦截器?

Spring MVC拦截器是Spring框架中的一个组件,用于拦截请求并在请求处理之前或之后执行一些额外的操作。它可以用于实现一些通用的、与业务无关的功能,如日志记录、权限验证、异常处理、跨域请求处理等。

拦截器在请求到达DispatcherServlet之后,但在具体的Controller方法执行之前,提供了一个拦截点,可以对请求进行处理和干预。拦截器可以拦截请求、响应或会话的各个阶段,并在每个阶段执行预定义的操作。

3.2 什么是过滤器

依赖于servlet容器。在实现上基于函数回调,可以对几乎所有请求进行过滤,但是缺点是一个过滤器实例只能在容器初始化时调用一次。使用过滤器的目的是用来做一些过滤操作,比如:在过滤器中修改字符编码;在过滤器中修改HttpServletRequest的一些参数,包括:过滤低俗文字、危险字符等

3.3 拦截器与过滤器的区别?

  • 过滤器(filter)

    1.filter属于Servlet技术,只要是web工程都可以使用

  • 2.filter主要由于对所有请求过滤

    3.filter的执行时机早于Interceptor

  • 拦截器(interceptor)

    1.interceptor属于SpringMVC技术,必须要有SpringMVC环境才可以使用

    2.interceptor通常由于对处理器Controller进行拦截

    3.interceptor只能拦截dispatcherServlet处理的请求

3.4 应用场景

  • 日志记录:记录请求信息的日志,以便进行信息监控、信息统计、计算PV(Page View)等。

  • 权限检查:如登录检测,进入处理器检测是否登录,如果没有直接返回到登录页面;

  • 性能监控:有时候系统在某段时间莫名其妙的慢,可以通过拦截器在进入处理器之前记录开始时间,在处理完后记录结束时间,从而得到该请求的处理时间(如果有反向代理,如apache可以自动记录);

  • 通用行为:读取cookie得到用户信息并将用户对象放入请求,从而方便后续流程使用,还有如提取Locale、Theme信息等,只要是多个Controller中的处理方法都需要的,我们就可以使用拦截器实现

四,拦截器快速入门

定义一个包并创建OneInterceptor类

拦截器(interceptor):

package com.Bingzy.interceptor;

import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class OneInterceptor implements HandlerInterceptor {
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        System.out.println("【OneInterceptor】:preHandle...");

        return true;
    }

    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
        System.out.println("【OneInterceptor】:postHandle...");

    }

    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
        System.out.println("【OneInterceptor】:afterCompletion...");
    }
}
  • spring-mvc.xml配置自定义拦截器

<mvc:interceptors>
        <bean class="com.Bingzy.interceptor.OneInterceptor"></bean>
</mvc:interceptors>

拦截器(interceptor)中的preHandle()方法中的返回值为true未拦截的情况:

SpringMVC中的JSR303与拦截器的使用,状态模式,mybatis,开发语言,java,intellij-idea,spring

拦截器(interceptor)中的preHandle()方法中的返回值为false拦截的情况: 

 注意:拦截器会根据preHandle()方法返回值进行拦截判断,返回了一个true值。这个返回值表示该拦截器已经处理了当前的请求,并且可以继续向下传递请求。如果返回false,则表示该拦截器不处理当前请求,请求将被终止 

4.1 拦截器原理图

SpringMVC中的JSR303与拦截器的使用,状态模式,mybatis,开发语言,java,intellij-idea,spring

  • preHandle:用于对拦截到的请求进行预处理,方法接收布尔(true,false)类型的返回值,返回true:放行,false:不放行。

    执行时机:在处理器方法执行前执行

    方法参数

    参数 说明
    request 请求对象
    response 响应对象
    handler 拦截到的方法处理
  • postHandle:用于对拦截到的请求进行后处理,可以在方法中对模型数据和视图进行修改

    执行时机:在处理器的方法执行后,视图渲染之前

    方法参数

    参数 说明
    request 请求对象
    response 响应对象
    handler 拦截到的处理器方法
    ModelAndView 处理器方法返回的模型和视图对象,可以在方法中修改模型和视图
  • afterCompletion:用于在整个流程完成之后进行最后的处理,如果请求流程中有异常,可以在方法中获取对象

    执行时机:视图渲染完成后(整个流程结束之后)

    方法参数

    参数 说明
    request 请求参数
    response 响应对象
    handler 拦截到的处理器方法
    ex 异常对象

4.2 拦截器链

    如果多个拦截器能够对相同的请求进行拦截,则多个拦截器会形成一个拦截器链,主要理解拦截器链中各个拦截器的执行顺序。拦截器链中多个拦截器的执行顺序,根拦截器的配置顺序有关,先配置的先执行

拦截器(interceptor)

package com.Bingzy.interceptor;

import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class TwoInterceptor implements HandlerInterceptor {
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        System.out.println("【TwoInterceptor】:preHandle...");

        return true;
    }

    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
        System.out.println("【TwoInterceptor】:postHandle...");

    }

    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
        System.out.println("【TwoInterceptor】:afterCompletion...");
    }
}

spring-mvc.xml配置自定义拦截器

<mvc:interceptors>
        <!--2) 多拦截器(拦截器链)-->
        <mvc:interceptor>
            <mvc:mapping path="/**"/>
            <bean class="com.Bingzy.interceptor.OneInterceptor"/>
        </mvc:interceptor>
        <mvc:interceptor>
            <mvc:mapping path="/book/**"/>
            <bean class="com.Bingzy.interceptor.TwoInterceptor"/>
        </mvc:interceptor>
</mvc:interceptors>

运行展示:

SpringMVC中的JSR303与拦截器的使用,状态模式,mybatis,开发语言,java,intellij-idea,spring

五,用户登录权限案例 

登入拦截器(interceptor):

package com.Bingzy.interceptor;

import org.springframework.web.servlet.HandlerInterceptor;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class LoginInterceptor implements HandlerInterceptor {
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        System.out.println("【implements】:preHandle...");
        StringBuffer url = request.getRequestURL();
        if (url.indexOf("/login") > 0 || url.indexOf("/logout") > 0){
            //        如果是 登录、退出 中的一种
            return true;
        }
//            代表不是登录,也不是退出
//            除了登录、退出,其他操作都需要判断是否 session 登录成功过
        String bname = (String) request.getSession().getAttribute("bname");
        if (bname == null || "".equals(bname)){
            response.sendRedirect("/page/book/login");
            return false;
        }
        return true;
    }

}

spring-mvc.xml配置自定义登入拦截器

<mvc:interceptors>
            <bean class="com.Bingzy.interceptor.LoginInterceptor"></bean>
</mvc:interceptors>

Controller层(web):

package com.Bingzy.web;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;

@Controller
public class LoginController {
    @RequestMapping("/login")
    public String login(HttpServletRequest req){
        String bname = req.getParameter("bname");
        HttpSession session = req.getSession();
        if ("zs".equals(bname)){
            session.setAttribute("bname",bname);
        }
        return "redirect:/book/list";
    }

    @RequestMapping("/logout")
    public String logout(HttpServletRequest req){
        req.getSession().invalidate();
        return "redirect:/book/list";
    }
}

login.jsp:

简单的测试布局,可自行布局

SpringMVC中的JSR303与拦截器的使用,状态模式,mybatis,开发语言,java,intellij-idea,spring

测试结果:

 SpringMVC中的JSR303与拦截器的使用,状态模式,mybatis,开发语言,java,intellij-idea,spring

总结

   如果用户发送URL中的后缀包含"/login"或"/logout",则表示当前请求是登录或退出操作,直接返回true表示继续处理请求,后端进行判断“uname”是否为“zs”,如果不是zs则域对象不会保存,从而到拦截器判断域对象为空则会重定向到登良页面,如果不为空就执行后端返回的字符串到视图解析器解析跳转指定页面文章来源地址https://www.toymoban.com/news/detail-729929.html

到了这里,关于SpringMVC中的JSR303与拦截器的使用的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • Spring-MVC使用JSR303及拦截器,增强网络隐私安全

    目录 一、JSR303 ( 1 )  是什么 ( 2 )  作用 ( 3 )  常用注解 ( 4 )  入门使用 二、拦截器 2.1  是什么 2.2  拦截器与过滤器的区别 2.3  应用场景 2.4 基础使用 2.5 用户登录权限控制 给我们带来的收获 JSR 303是Java规范请求(Java Specification Request)的一部分, 它定义了一套标准的Jav

    2024年02月09日
    浏览(43)
  • 学习 [Spring MVC] 的JSR 303和拦截器,提高开发效率

                                                   🎬 艳艳耶✌️ :个人主页                                                  🔥 个人专栏 : 《推荐】Spring与Mybatis集成整合》                                                  ⛺️    生活的理想,不断更

    2024年02月09日
    浏览(46)
  • SpringMVC中拦截器的简单使用

    步骤一:创建拦截器类 首先,我们需要创建一个拦截器类,该类需要实现 HandlerInterceptor 接口。这个接口定义了三个方法,分别在请求处理前、请求处理后和视图渲染后执行。 步骤二:创建配置类 上述配置类使用了 @Configuration 注解,表示这是一个配置类。通过 @Bean 注解将

    2024年01月17日
    浏览(42)
  • SpringMVC中的拦截器不生效的问题解决以及衍生出的WebMvcConfigurationSupport继承问题思考

    过滤器代码(被Spring扫描并管理): 过滤器配置代码: 按理说我们发出请求 localhost/stu 之后,应该可以看到过滤器的效果,但是失效了。 网上的说法众说纷纭: 没加@Component或者@Configuration注解 @ComponentScan没扫描到 路径配置错了 以上三种说法一一排除之后,我发现一个博客提

    2024年02月01日
    浏览(36)
  • 【SpringMVC】| SpringMVC拦截器

    目录 一:SpringMVC拦截器 1. 拦截器介绍 2. HandlerInterceptor接口分析 3. 自定义拦截器实现权限验证 SpringMVC 中的 Interceptor 拦截器,它的主要作用是拦截指定的用户请求,并进行相应的预处理与后处理。其拦截的时间点在“处理器映射器根据用户提交的请求映射出了所要执行的处理

    2024年02月06日
    浏览(43)
  • SpringMVC:拦截器

    一般我们会做一些统一的操作这个时候我们需要使用springmvc提供的拦截器,例如token的验证,字段必填的操作,接口超时判断,签名验证,字段加密等操作,所以我们需要了解执行先后顺序。 我们来简单介绍下实现过程及对应代码,执行结果: 1、定义自己的spring mvc拦截器需

    2024年01月24日
    浏览(42)
  • springMVC之拦截器

    拦截器 SpringMVC中的拦截器用于拦截控制器方法的执行 SpringMVC中的拦截器需要实现HandlerInterceptor SpringMVC的拦截器必须在SpringMVC的配置文件中进行配置: FirstIntercepor类: SecondInterceptor类: SpringMVC中的拦截器有三个抽象方法: preHandle:控制器方法执行之前执行preHandle(),其bool

    2024年02月10日
    浏览(36)
  • SpringMVC 拦截器

    Spring MVC 拦截器是Spring框架中的一种机制,用于在请求到达处理器之前和渲染视图之前拦截请求,并允许开发者在这两个时间点进行自定义的处理逻辑。拦截器与过滤器(Filter)类似,但更加专注于对请求的处理器的拦截,比如对访问权限进行控制、日志记录、性能监控等。

    2024年01月19日
    浏览(43)
  • 一文学会 SpringMVC 拦截器

    ✅作者简介:2022年 博客新星 第八 。热爱国学的Java后端开发者,修心和技术同步精进。 🍎个人主页:Java Fans的博客 🍊个人信条:不迁怒,不贰过。小知识,大智慧。 💞当前专栏:SSM 框架从入门到精通 ✨特色专栏:国学周更-心性养成之路 🥭本文内容:一文学会 SpringM

    2024年02月02日
    浏览(48)
  • 12、SpringMVC之拦截器

    创建名为spring_mvc_interceptor的新module,过程参考9.1节和9.5节 与自定义的过滤器一样,自定义的拦截器也要配置后才能生效; 过滤器是服务器中的组件,所以配置到 web.xml 中; 拦截器是 springmvc 中的组件,因此要配置到 springmvc 的配置文件中。 因为在配置拦截器时,没有指定要

    2024年02月05日
    浏览(45)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包