目录
- 前言
- 1. 基本知识
- 2. Demo
前言
基本的Java知识推荐阅读:
- java框架 零基础从入门到精通的学习路线 附开源项目面经等(超全)
- 【Java项目】实战CRUD的功能整理(持续更新)
从实战中学习:
常用在一些重复代码,需要进行过滤的
1. 基本知识
FilterChain 是 Java 中 Servlet 过滤器机制的重要组成部分,定义了过滤器链的执行顺序和执行逻辑
FilterChain 主要用于控制多个过滤器的依次执行,直到所有过滤器都完成后再交由最终的目标资源(如 Servlet 或 JSP)处理请求
执行流程:
- 过滤器的定义和顺序:多个过滤器会在 web.xml 文件中配置,或者在代码中使用注解(如 @WebFilter)声明
- 过滤器链的构建:容器会根据配置或注解扫描到的过滤器,按顺序构建一个过滤器链(FilterChain)
- 执行顺序:请求到达后,第一个过滤器执行后调用 FilterChain.doFilter() 方法,传递请求到下一个过滤器,依次进行
- 最终资源处理:当过滤器链上的最后一个过滤器执行完毕后,调用目标资源(如 Servlet),开始响应流程
- 响应的返回:执行完目标资源后,响应会沿着过滤器链的反方向依次返回,使每个过滤器有机会处理响应
基本的工作原理如下:
核心方法是 doFilter(ServletRequest request, ServletResponse response),用于将请求和响应传递到过滤器链的下一个过滤器或目标资源
- doFilter 方法:每个过滤器在其 doFilter 方法中调用 chain.doFilter(request, response),会将请求传递到下一个过滤器或目标资源
- 处理请求和响应:过滤器可以在调用 chain.doFilter() 前后执行逻辑,从而对请求和响应进行处理
例如,日志记录、权限校验、编码设置等
2. Demo
一个简单的 FilterChain 示例,展示了两个过滤器(LoggingFilter 和 AuthenticationFilter)如何在 FilterChain 中按顺序工作
1.定义第一个过滤器:LoggingFilter
package FilterChain知识;import org.springframework.stereotype.Component;import javax.servlet.*;
import javax.servlet.annotation.WebFilter;
import java.io.IOException;@Component
@WebFilter(urlPatterns = "/demo/*")
public class LoggingFilter implements Filter {@Overridepublic void init(FilterConfig filterConfig) {System.out.println("LoggingFilter 初始化");}@Overridepublic void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {System.out.println("LoggingFilter: 请求开始...");// 执行下一个过滤器或目标资源chain.doFilter(request, response);System.out.println("LoggingFilter: 响应返回...");}@Overridepublic void destroy() {System.out.println("LoggingFilter 销毁");}
}
2.定义第二个过滤器:AuthenticationFilter
import org.springframework.stereotype.Component;import javax.servlet.*;
import javax.servlet.annotation.WebFilter;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import java.io.IOException;@Component
@WebFilter(urlPatterns = "/demo/*")
public class AuthenticationFilter implements Filter {@Overridepublic void init(FilterConfig filterConfig) {System.out.println("AuthenticationFilter 初始化");}@Overridepublic void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {HttpServletRequest httpRequest = (HttpServletRequest) request;Cookie[] cookies = httpRequest.getCookies();System.out.println(cookies);if (cookies != null) {for (Cookie cookie : cookies) {System.out.println("Found cookie: " + cookie.getName() + "=" + cookie.getValue());}}// 继续执行过滤器链chain.doFilter(request, response);}@Overridepublic void destroy() {System.out.println("AuthenticationFilter 销毁");}
}
3.定义目标资源:DemoServlet
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;@WebServlet("/demo/process")
public class DemoServlet extends HttpServlet {@Overrideprotected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {System.out.println("DemoServlet: 处理请求...");resp.getWriter().write("Hello, FilterChain!");}
}
4.执行流程和结果
当访问 http://localhost:8080/demo/process
时,过滤器链将按顺序执行,以下是执行过程和输出顺序:
- LoggingFilter 开始处理请求
- AuthenticationFilter 进行身份验证
- DemoServlet 处理实际请求并生成响应
- 过滤器以相反顺序返回响应处理
大致的结果如下:
LoggingFilter 初始化
AuthenticationFilter 初始化
LoggingFilter: 请求开始...
AuthenticationFilter: 检查身份验证...
DemoServlet: 处理请求...
AuthenticationFilter: 响应返回后执行...
LoggingFilter: 响应返回...