Spring MVC拦截器

Spring MVC的静态概念

  • DispatcherServlet:浏览器用户请求分发到达合适的Controller,生产业务数据Model,Model通过DispatcherServlet传递给View来完成最终的页面呈现。MVC将业务逻辑和页面的分离其实核心就是通过DispatcherServlet实现的。

  • HandleAdapter:DispatcherServlet内部使用的一个类,Controller的一个表现形式。SpringMVC中并没有一个interface叫做Controller,DispatcherServlet其实最终调用的Controller是以Handler形式出现的。HandleAdapter适配器模式,将各种不同类型的Handler适配成DispatcherServlet可以使用的Handler。

  • HandlerInterceptor:拦截器的意思,在调用Controller之前,调用之后已经最终在Model或View发生到页面完成呈现之后可以做很多事情。

  • HandlerMapping:DispatcherServlet前端控制器与我们Controller映射关系的一种类。HandlerMapping工作完毕之后,给我们的DispatcherServlet一个HandleAdapter,这个HandleAdapter中就包括了核心的内容是具体的Controller实例,以及这个Controller需要被包裹的HandlerInterceptor,构成一个执行的链条向下走。

  • HandlerExecutionChain:HandlerMapping返回HandleAdapter以及HandlerInterceptor,他们之间构成了执行链条:preHandle -----> Controller method ------> postHandle ------> afterCompletion

  • ModelAndView:Model的具体表现,或者用Model或者Map实现,最后都会由DispatcherServlet都会统统转换成ModelAndView

  • ViewResolver:告诉DispatcherServlet需要用哪个视图来进行视图的呈现,作用就是根据配置找出那一个我们需要的视图对象,比如JSTL

  • View:JSP,JSTL负责呈现页面

Spring MVC的动态概念

什么是拦截器

拦截器是指通过统一拦截从浏览器发往服务器的请求来完成功能的增强。

使用场景:解决请求的共性问题(如:乱码问题、权限验证问题等)

拦截器实现:

1、编写拦截器类实现HandlerInterceptor接口

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

@Controller
@RequestMapping("/")
public class IndexController {
    @RequestMapping("/viewAll")
    public ModelAndView viewAll(String name, String pwd) {
    ModelAndView mv = new ModelAndView();
    mv.setViewName("/hello.jsp");
    mv.addObject("msg","从viewAll方法传回视图的数据!")
        return mv;
    }
}
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

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

public class TestInterceptor implements HandlerInterceptor {

  public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
      System.out.println("执行到了afterCompletion方法!");
  }

  public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler,ModelAndView modelAndView) throws Exception {
    // 可以通过ModelAndView参数来改变显示的视图,或修改发往视图的方法
    modelAndView.addObject("msg","这里传回的是被拦截器修改之后的消息!");
    modelAndView.setViewName("/hello2.jsp");
    System.out.println("执行到了postHandle方法!");
  }

  // 返回值:表示我们是否需要将当前的请求拦截下来
  // 如果返回false:请求将被终止;true:请求会被继续运行
  // Object handler:被拦截的请求的目标对象,及IndexController的实例对象
  public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        request.setCharacterEncoding("UTF-8");  // 和过滤器解决乱码效果一样
        System.out.println("执行到了preHandle方法!");
        // 对用户是否登录进行判断
        if(request.getSession().getAttribute("user") == null){
        // 如果用户没有登录,就终止请求,并发送到登录页面
        request.getRequestDispatcher("/login.jsp").forward(arg0,arg1);
        return false ;
      }

      return true;
  }
}

2、将拦截器注册进SpringMVC框架中(spring-mvc.xml)

3、配置拦截器的拦截规则


   


  
   
       
  

  • 拦截方法介绍:
    • 1、preHandle方法,在请求被处理之前进行调用。
    • 2、postHandle方法,在请求被处理之后进行调用。
    • 3、afterCompletion方法,在请求结束之后才进行调用。
多个拦截器协同时工作流程图
多个拦截器协同时工作流程图
拦截器的其他实现方式
  • 拦截器的类还可以通过实现WebRequestInterceptor接口来编写
  • 向SpringMVC框架注册的写法不变
public class TestInterceptor2 implements WebRequestInterceptor {

    public void afterCompletion(WebRequest arg0, Exception ex) throws Exception {
        System.out.println("执行到了afterCompletion方法!");
    }

    public void postHandle(WebRequest arg0, ModelAndView modelAndView) throws Exception {
        System.out.println("执行到了postHandle方法!");
    }

    public void preHandle(WebRequest arg0) throws Exception {
        System.out.println("执行到了preHandle方法!");
    }

}
拦截器的使用场景

使用原则:处理所有请求的共同问题
1、解决乱码问题
2、解决权限验证问题

拦截器与过滤器的区别
  • 过滤器Filter依赖于Servlet容器,基于回调函数,过滤范围大
  • 拦截器Interceptor依赖于框架容器,基于反射机制,只过滤请求

你可能感兴趣的:(Spring MVC拦截器)