在第一节写SpringMVC的运行原理的时候讲过,每个组件之间都是按部就班的运行的,如下图(部分图):

都是按步骤每步每步走,当请求没有发送,前端控制器没收到请求,就不会去找处理器映射器。Controller是使用了Servlet为核心,因为是SpringMVC使用了Servlet为核心,那么每个请求都会拦截下来运行,那么我们想要在它运行前后先拦截下来进行条件判断,这样就出现了拦截器。那怎么用代码实现使用拦截器呢?首先搭建环境
Maven配置
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>
<spring.version>5.0.2.RELEASE</spring.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>servlet-api</artifactId>
<version>2.5</version> <scope>provided</scope>
</dependency>
<dependency>
<groupId>javax.servlet.jsp</groupId>
<artifactId>jsp-api</artifactId>
<version>2.0</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.11</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.9.0</version>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-core</artifactId>
<version>2.9.0</version>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-annotations</artifactId>
<version>2.9.0</version>
</dependency>
<dependency>
<groupId>commons-fileupload</groupId>
<artifactId>commons-fileupload</artifactId>
<version>1.3.1</version>
</dependency>
<dependency>
<groupId>commons-io</groupId>
<artifactId>commons-io</artifactId>
<version>2.4</version>
</dependency>
<dependency>
<groupId>com.sun.jersey</groupId>
<artifactId>jersey-core</artifactId>
</dependency>
<dependency>
<groupId>com.sun.jersey</groupId>
<artifactId>jersey-client</artifactId>
<version>1.18.1</version>
</dependency>
</dependencies>
web.xml
<servlet>
<servlet-name>dispatcherServlet</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>ContextConfigLocation</param-name>
<param-value>classpath:SpringMVC.xml</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>dispatcherServlet</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
<filter>
<filter-name>characterEncodingFilter</filter-name>
<filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
<init-param>
<param-name>Encoding</param-name>
<param-value>UTF-8</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>characterEncodingFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
SpringMVC.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:mvc="http://www.springframework.org/schema/mvc"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans
https://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
https://www.springframework.org/schema/context/spring-context.xsd
http://www.springframework.org/schema/mvc
https://www.springframework.org/schema/mvc/spring-mvc.xsd">
<!--开启mvc配置注解-->
<mvc:annotation-driven></mvc:annotation-driven>
<!--视图解析器-->
<bean id="internalResourceViewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="prefix" value="/WEB-INF/pages/"></property>
<property name="suffix" value=".jsp"></property>
</bean>
<!--需要扫描的包-->
<context:component-scan base-package="com.itheima"></context:component-scan>
<!--设置静态文件不拦截-->
<mvc:resources mapping="/pages/css/" location="/pages/css/**"></mvc:resources>
<mvc:resources mapping="/pages/js/" location="/pages/js/**"></mvc:resources>
<mvc:resources mapping="/pages/images/" location="/pages/images/**"></mvc:resources>
</beans>
index.jsp
<%@ page contentType="text/html;charset=UTF-8" language="java" isELIgnored="false"%>
<html>
<head>
</head>
<body>
<h3>拦截器</h3>
<a href="user/testInterceptor">拦截器</a>
</body>
</html>
seccess.jsp
<%@ page contentType="text/html;charset=UTF-8" language="java" isELIgnored="false"%>
<html>
<head>
</head>
<body>
<h3>执行成功</h3>
<% System.out.println("success.jsp执行了"); %>
</body>
</html>
自定义拦截器——需要实现HandlerInterceptor
里面有三个可重写的方法。
①
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
return false;
}
这是预处理方法,在执行Controller方法前执行方法。
返回值如果是true则代表可以通过拦截器,执行下一个拦截器,如果没有的话就执行Controller方法。
返回值如果是false则代表不能通过拦截器。
②
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
}
这是后处理方法,在Controller方法执行完以后执行
③
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
}
这是最后进行的方法。执行完跳转页面以后再执行。
第一个拦截器
package com.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 setInterceptor implements HandlerInterceptor {
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
System.out.println("预处理执行器1执行了");
return true;
}
//后处理方法,controller方法执行完,在执行这个方法
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
System.out.println("后处理执行器1执行了");
}
//success.jsp页面执行后,该方法会执行
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
System.out.println("最后处理执行器1执行了");
}
}
第二个拦截器
package com.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 setDoubleInterceptor implements HandlerInterceptor {
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
System.out.println("预处理执行器2执行了");
return true;
}
//后处理方法,controller方法执行完,在执行这个方法
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
System.out.println("后处理执行器2执行了");
}
//success.jsp页面执行后,该方法会执行
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
System.out.println("最后处理执行器2执行了");
}
}
写Controller方法
package com;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
@Controller
@RequestMapping("/user")
public class controller {
@RequestMapping("/testInterceptor")
public String testInterceptor(){
System.out.println("执行testInterceptor方法");
return "success";
}
}
测试结果:

可以看到执行顺序为:

拦截器1的预处理运行完,到拦截器2的预处理器,再到Controller;此时后处理器开始,是由Controller按顺序返回,则到拦截器2的后处理执行器执行,再到拦截器1;最后success.jsp执行完以后再到拦截器2的最后处理执行器完成,才到拦截器1。

本文介绍了在SSM框架中使用拦截器进行条件判断的实现过程,包括Maven配置、web.xml、SpringMVC.xml的设置,以及自定义拦截器的创建。详细讲解了HandlerInterceptor接口的三个方法,预处理方法、后处理方法和最终处理方法,并通过示例展示了拦截器的执行顺序,实现了对Controller方法执行前后的控制。
1402

被折叠的 条评论
为什么被折叠?



