在现代Web应用程序开发中,尤其是在使用SpringBoot框架构建项目时,理解并有效利用拦截器(Interceptor)和过滤器(Filter)对于增强应用程序的功能性、安全性和可维护性至关重要。
拦截器和过滤器作为控制请求处理流程中的重要组件,它们在不同的层级上对进入和离开应用程序的请求进行预处理和后处理操作。
SpringBoot拦截器(Interceptor)
概念与作用: SpringBoot拦截器是基于Java的面向切面编程(AOP)思想实现的,它允许开发者在业务处理过程中的特定点插入额外的处理逻辑,而不必修改核心业务代码。
拦截器主要用于处理业务逻辑相关的拦截需求,例如权限验证、日志记录、事务管理等。
拦截器通常在Spring MVC的DispatcherServlet内部工作,因此它只对Spring MVC处理的请求生效,不适用于静态资源。
代码实现示例:
创建一个简单的拦截器类:
import org.springframework.stereotype.Component;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;@Component
public class LoggingInterceptor implements HandlerInterceptor {@Overridepublic boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {System.out.println("Before the request is handled: " + request.getRequestURI());return true; // 返回true表示继续处理请求,false表示中断请求}@Overridepublic void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {System.out.println("After the request is handled, before rendering view.");}@Overridepublic void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {System.out.println("Request completed. Cleaning up resources if any.");}
}
在配置类中注册拦截器:
import org.springframework.beans.factory.annotation.Autowired;
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 {@Autowiredprivate LoggingInterceptor loggingInterceptor;@Overridepublic void addInterceptors(InterceptorRegistry registry) {registry.addInterceptor(loggingInterceptor).addPathPatterns("/**") // 拦截所有请求.excludePathPatterns("/excludePath"); // 排除某些路径}
}
SpringBoot过滤器(Filter)
概念与作用: 过滤器是Servlet规范的一部分,它可以对进入应用的所有HTTP请求和响应进行预处理和后处理操作,无论这些请求是否由Spring MVC处理。
过滤器常用于处理跨域请求、字符编码转换、安全验证等通用任务。
代码实现示例:
创建一个简单的过滤器类:
import javax.servlet.*;
import javax.servlet.http.HttpServletRequest;
import java.io.IOException;public class CharacterEncodingFilter implements Filter {@Overridepublic void init(FilterConfig filterConfig) throws ServletException {// 初始化操作}@Overridepublic void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {HttpServletRequest httpRequest = (HttpServletRequest) request;System.out.println("Filtering request to " + httpRequest.getRequestURI());request.setCharacterEncoding("UTF-8");response.setCharacterEncoding("UTF-8");chain.doFilter(request, response); // 继续执行下一个过滤器或请求处理器}@Overridepublic void destroy() {// 清理资源}
}
在SpringBoot应用中注册过滤器,可以通过实现WebMvcConfigurer
接口或直接使用@Component
和@Order
注解(需要Spring Boot 2.4+版本):
// 使用WebMvcConfigurer接口注册
@Configuration
public class FilterConfig implements WebMvcConfigurer {@Autowiredprivate CharacterEncodingFilter characterEncodingFilter;@Overridepublic void addFilters(FilterRegistrationBean<Filter> registry) {registry.addFilter(characterEncodingFilter, "/*").addInitParameter("paramName", "paramValue").setOrder(1); // 设置执行顺序}
}// 或者使用@Component和@Order(Spring Boot 2.4+)
@Component
@Order(1)
public class CharacterEncodingFilter extends OncePerRequestFilter { /* ... */ }
区别总结:
-
触发时机:过滤器先于拦截器执行,过滤器在请求进入Servlet之前和响应返回给客户端之前工作;拦截器则在Spring MVC的请求处理流程中,更靠近业务逻辑层。
-
依赖性:过滤器依赖于Servlet容器,是Servlet规范的一部分;拦截器是Spring框架特有的,不依赖于Servlet容器。
-
功能范围:过滤器可以对所有进出Web应用的数据流进行操作,包括静态资源;拦截器主要针对Spring MVC的请求处理流程,通常不处理静态资源。
-
实现方式:过滤器基于函数回调机制;拦截器通常基于Java的反射机制(动态代理)实现。
-
资源访问:拦截器可以访问Spring的IOC容器,可以直接使用Spring管理的Bean;而过滤器则不行,除非手动实现Spring的依赖注入。
通过以上对比和代码示例,可以看出拦截器和过滤器在SpringBoot应用中各有侧重点和适用场景,选择使用哪种机制取决于具体的业务需求。