Filter(过滤器)

Filter

简介

Filter是对客户端访问资源的过滤,符合条件的放行,不符合条件的不放行,并且可以对目标资源访问前后进行逻辑处理的一个组件。

过滤器的作用

​ Java过滤器是处于客户端与服务器资源文件之间的一道过滤网,在访问资源文件之前,通过一系列的过滤器可以对请求进行修改、判断等,把不符合规则的请求在中途拦截或修改;也可以对响应进行过滤,拦截或修改响应。例如:修改响应体或是请求体的字符集。


快速入门

  • 步骤:
    • 使用Maven创建一个Web项目
    • 导入javax.servlet-api依赖
    • 编写一个过滤器继承Filter执行过滤操作
    • 编写一个Servlet继承HttpServlet执行业务处理操作
    • web.xml/注解中进行配置(配置servletfilter

CharsetFilter.java

public class CharsetFilter implements Filter {

    @Override
    public void init(FilterConfig filterConfig) throws ServletException {
        System.out.println("这里做一些初始化操作");
    }

    @Override
    public void destroy() {
        System.out.println("这里做一些过滤器被销毁前的操作");
    }

    @Override
    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
        System.out.println("这里执行过滤请求");
        //比如将请求的字符集改为utf-8
        request.setCharacterEncoding("utf-8");
        System.out.println(request.getCharacterEncoding());

        //这里也可以设置响应体的相关参数
        System.out.println(response.getCharacterEncoding());
        //改后放行
        chain.doFilter(request,response);

        System.out.println("这里过滤响应");
        System.out.println(response.getCharacterEncoding());

    }
}

ServiceServlet.java

public class ServiceServlet extends HttpServlet {
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        resp.setContentType("text/html;charset=utf-8");
        PrintWriter out = resp.getWriter();
        out.println(req.getParameter("name"));
    }
}

web.xml

<!--    注册servlet-->
    <servlet>
        <servlet-name>servlet</servlet-name>
        <servlet-class>servlet.ServiceServlet</servlet-class>
<!--        <load-on-startup>0</load-on-startup>-->
    </servlet>
    <servlet-mapping>
        <servlet-name>servlet</servlet-name>
        <url-pattern>/servlet</url-pattern>
    </servlet-mapping>
    <filter>
        <filter-name>filter</filter-name>
        <filter-class>filter.CharsetFilter</filter-class>
    </filter>
    <filter-mapping>
        <filter-name>filter</filter-name>
        <servlet-name>servlet</servlet-name> 
        <url-pattern>/servlet</url-pattern>
    </filter-mapping>

xml配置

url-pattern:代表要过滤的资源的匹配

filter-name:过滤器名称 用于映射 于servlet-name作用相同

filter-class: 过滤器类的全限定名称

servlet-name:代表要过滤的Servlet的资源匹配


Filter的生命周期其与生命周期相关的方法

Filter接口有三个方法,这三个方法都与Filter的生命后期有关。

  • init(FilterConfig): 代表filter对象初始化方法,filter对象由tomcat创建并且会将配置文件(web.xml)生成一个FilterConfig对象注入其中。
  • doFilter(ServletRequest,ServletResponse,FilterChain): 代表filter对象执行过滤的核心方法如果某资源在已经被配置到这个filter进行过滤的话,那么每次访问这个资源都会执行doFilter()方法,与ServletService()方法类似。
  • destory(): 代表filter销毁的方法,这里可以执行一些销毁前的操作, 当filter对象销毁时会执行这个方法。

Filter对象的生命周期

  • Filter何时创建:服务器启动时就创建该filter对象
  • Filter合适销毁: 服务器关闭时filter销毁

注意:FilterServlet一样都是默认单例的。


Filter相关API

  1. init(FilterConfig)

    1. Filter创建时会去执行的init方法
    2. 参数FilterConfig代表该Filter对象配置信息的对象,内部封装的是该Filter的配置信息。由Tomcat创建该Filter对象时从配置文件中读取封装为一个FilterConfig后注入。
  2. destroy()

    1. filter对象销毁时执行
    2. 这里可以执行一些销毁前需要执行的操作,因为filter对象销毁时该方法会被执行
  3. doFilter(ServletRequest,ServletResponse,FilterChain)

    1. 当该filter映射的url-pattern对应的资源被访问了 会执行该方法

    2. 其中的参数

      • ServletRequest/ServletResponse:每次在执行doFilter方法时 web容器负责创建一个request和一个response对象作为doFilter的参数传递进来。该requestresponse就是在访问目标资源的service方法时的requestresponse
      • FilterChain: 过滤器链对象, 通过该对象的doFilter方法可以放行该请求,如果该过滤器上还有过滤器没有过滤该请求,那么转交给它,如果没有则直接到达Servletservice()

过滤器链

​ 在一个 Web 应用程序中可以注册多个 Filter 程序,每个 Filter 程序都可以针对某一个 URL 进行拦截。如果多个 Filter 程序都对同一个 URL 进行拦截,那么这些 Filter 就会组成一个Filter 链(也称过滤器链)。

Filter链

  • 拦截顺序和过滤器web.xml注册顺序(filter-mapping)一致。
  • 由上图可知过滤器链过滤的顺序准许"先进后出"的原则。

过滤器链代码演示

Servlet.java

public class Servlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        resp.setContentType("html/text;charset=utf-8");
        PrintWriter out = resp.getWriter();
        System.out.println("请求已接受");
        out.println("请求已接受");
    }
}

Filter01.java

public class Filter01 implements Filter {
    @Override
    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
        System.out.println("请求经过过滤器01");
        chain.doFilter(request,response);
        System.out.println("响应经过过滤器01");
    }
}

Filter02.java

public class Filter02 implements Filter {
    @Override
    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
        System.out.println("请求经过过滤器02");
        chain.doFilter(request,response);
        System.out.println("响应经过过滤器02");
    }
}

web.xml

    <servlet>
        <servlet-name>servlet</servlet-name>
        <servlet-class>servlet.Servlet</servlet-class>
    </servlet>
    <servlet-mapping>
        <servlet-name>servlet</servlet-name>
        <url-pattern>/filterServlet</url-pattern>
    </servlet-mapping>
<!--    过滤器链注册-->

    <filter>
        <filter-name>filter01</filter-name>
        <filter-class>filter.Filter01</filter-class>
    </filter>
    <filter-mapping>
        <filter-name>filter01</filter-name>
        <url-pattern>/filterServlet</url-pattern>
    </filter-mapping>
    <filter>
        <filter-name>filter02</filter-name>
        <filter-class>filter.Filter02</filter-class>
    </filter>
    <filter-mapping>
        <filter-name>filter02</filter-name>
        <url-pattern>/filterServlet</url-pattern>
    </filter-mapping>

控制台输出(可以看到 先进后出)

image-20220424163848783


Filterurl-pattern配置

  • 匹配单个资源

        <filter>
            <filter-name>filter02</filter-name>
            <filter-class>filter.Filter02</filter-class>
        </filter>
        <filter-mapping>
            <filter-name>filter02</filter-name>
            <url-pattern>/filterServlet</url-pattern>
        </filter-mapping>
    
  • 统配符匹配(最常使用)

        <filter>
            <filter-name>filter02</filter-name>
            <filter-class>filter.Filter02</filter-class>
        </filter>
        <filter-mapping>
            <filter-name>filter02</filter-name>
            <url-pattern>/*</url-pattern>
        </filter-mapping>
    
  • 扩展名匹配 (*.abc *.jsp注意不能和统配符混用

        <filter>
            <filter-name>filter02</filter-name>
            <filter-class>filter.Filter02</filter-class>
        </filter>
        <filter-mapping>
            <filter-name>filter02</filter-name>
            <url-pattern>*.jsp</url-pattern>
        </filter-mapping>
    

-End-

  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值