Servlet过滤器(Filter)介绍和使用[亲测有效]

Servlet过滤器(Filter)介绍和使用[亲测有效]通过实现Filter接口,我们可以实现一个拦截器,从而实现对目标请求的拦截。Filter本质上也是一个Java程序,它和Servlet一样也是被Servlet容器调用和执行的。 我们在实现了拦截器之后,在web.xml中注册并指定需要拦截的请求。当Servlet容器调用某个Se…

使用Servlet的拦截器,我们需要使用到3个接口:Filter、FilterChain、FilterConfig

下面我们来介绍一下这几个接口

Filter接口

通过实现Filter接口,我们可以实现一个拦截器,从而实现对目标请求的拦截。Filter本质上也是一个Java程序,它和Servlet一样也是被Servlet容器调用和执行的。

我们在实现了拦截器之后,在web.xml中注册并指定需要拦截的请求。当Servlet容器调用某个Servlet程序的时候,如果发现已经注册了一个Filter程序对请求进行拦截,那么容器不会直接调用Servlet程序的 service 方法,而是调用Filter程序的 doFilter 方法,由doFilter方法来决定是否调用 service 方法。

Filter.doFilter 方法不能直接调用 Servlet的 service方法,而是通过调用 FilterChain.doFilter()来调用目标Servlet的 service方法。FilterChain对象是通过 doFilter 方法的参数传过来的。

** java.servlet.Filter接口 ** 定义了 三个方法:init、doFilter、destroy

  1. init方法

应用程序启动时,Web容器会根据web.xml配置信息来创建每个注册的Filter实例,并保存在内存中。

当容器创建Filter对象时,会调用init方法。init方法在整个生命周期中,只会被调用一次。Web容器在调用整个方法的时候,会传递一个包含了Filter配置信息和运行环境信息的 FilterConfig 对象。

public voic init(FilterConfig filterConfig) throws ServletException
  1. doFilter方法

    当目标Servlet被请求的时候,Servlet会先调用Filter的 doFilter 方法。

    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws java.io.IOException.ServletException
    

    其中,参数request和response是Web容器会上一个Filter传递过来的请求和响应对象。参数Chain代表当前Filter链对象。

  2. destroy

    该方法在Web容器卸载Filter对象之前被调用,在Filter的整个生命周期中仅会被调用一次。一般用来释放被该Filter对象占用的资源,例如:关闭数据库连接和IO流。

Filter链

可以存在有多个Filter对同一请求进行拦截,这样就形成了Filter链。Filter链中的各个Filter的拦截顺序是它们在web.xml文件中的配置顺序。

上一个 Filter.doFilter() 方法调用的 FilterChain.doFilter 方法调用的是下一个 Filter.doFilter方法。最后一个 Filter.doFilter 方法调用的 FilterChain.doFilter方法调用的是 目标Servlet的service方法。

FilterChain接口

该接口用于定义一个Filter链对象应该向外提供的方法,这个接口只定义了一个doFilter方法。

public void doFilter(ServletRequest request, ServletResponse response) throws java.io.IOException.ServletException

FilterChain接口的doFilter方法用于通知Web容器把请求交给Filter链中的下一个Filter去处理,如果当前调用此方法的Filter对象是Filter链中的最后一个Filter,那么将把请求交给目标Servlet程序去处理。

FilterConfig接口

与Servlet程序类似,Filter程序可能也要访问Servlet容器。Servlet规范将代表ServletContext对象和Filter配置的参数信息都封装到一个叫做FilterConfig的对象中。

FilterConfig接口定义FilterConfig对象应该向外提供的方法,以便在Filter程序中可以调用这些方法来获取ServletContext对象,以及获取在web.xml文件中为Filter配置的名称和初始化参数。

定义方法如下:

  • getFilterName方法,返回 <filter-name>标签内的值

  • getServletContext方法,返回FilterConfig对象中所包装的对ServletContext对象的引用

  • getInitParameter方法,用于返回在web.xml文件中为Filter所设置的某个名称的初始化的参数值

  • getInitParameterNames方法,返回一个Enumeration集合对象

Filter的注册和映射

注册

<filter>
  <filter-name>logFilter</filter-name>
  <filter-class>com.xgc.filter.LogFilter</filter-class>
  <init-param>
		<param-name>encoding</param-name>
        <param-value>utf-8</param-value>
  </init-param>
</filter>

映射

Filter的映射方式分为两种:资源访问请求路径、访问请求方式

指定资源访问请求路径

<filter-mapping>
    <filter-name>logFilter</filter-name>
    <url-pattern>/*</url-pattern>
</filter-mapping>

拦截不同方式的请求路径

在web.xml文件中,每一个<filter-mapping>元素都可以配置一个Filter所拦截的资源。在<filter-mapping>元素中有一个特殊的子元素<dispatcher>,该元素用于指定过滤器所拦截的资源被Servlet容器调用的方式。具体如下:

  • REQUEST(默认)

    当用户直接访问Servlet,Web容器会调用过滤器。如果目标资源是通过RequestDispatcher 的 include 或 forward 方法访问时,那么该过滤器将不会被调用。

  • INCLUDE

    如果目标资源是通过RequestDispatcher 的 include方法访问时,那么该过滤器将被调用

  • FORWARD

    如果目标资源是通过RequestDispatcher 的 forward方法访问时,那么该过滤器将被调用

  • ERROR

    如果目标资源是通过声明式异常处理机制调用时,那么该过滤器将被调用。

使用例子

查看项目目录

Servlet过滤器(Filter)介绍和使用[亲测有效]

LogFilter:

package com.xgc.filter;

import javax.servlet.*;
import java.io.IOException;

public class LogFilter implements Filter {

    @Override
    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
        System.out.println("目标Servlet的service方法执行前");
        chain.doFilter(request, response);
        System.out.println("目标Servlet的service方法执行后");
    }
}

TestServlet:

package com.xgc.servlet;

import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServlet;
import java.io.IOException;

public class TestServlet extends HttpServlet {

    @Override
    public void service(ServletRequest req, ServletResponse res) throws ServletException, IOException {
        System.out.println("处理请求");
    }

}

web.xml

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"
         version="4.0">

    <servlet>
        <servlet-name>testServlet</servlet-name>
        <servlet-class>com.xgc.servlet.TestServlet</servlet-class>
    </servlet>
    <servlet-mapping>
        <servlet-name>testServlet</servlet-name>
        <url-pattern>/test</url-pattern>
    </servlet-mapping>

    <filter>
        <filter-name>logFilter</filter-name>
        <filter-class>com.xgc.filter.LogFilter</filter-class>
    </filter>
    <filter-mapping>
        <filter-name>logFilter</filter-name>
        <url-pattern>/test</url-pattern>
    </filter-mapping>
</web-app>

将项目运行起来,访问路径 http://localhost:8080/javaweb/test

在IDE控制台会发现下面输出:

Servlet过滤器(Filter)介绍和使用[亲测有效]

我们可以发现,通过拦截器,我们可以在目标Servlet的service方法执行前后进行其他处理。

参考文章

Filter、FilterChain、FilterConfig

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。
转载请注明出处: https://daima100.com/13542.html

(0)

相关推荐

  • 使用Python将数据写入CSV文件的完整指南

    使用Python将数据写入CSV文件的完整指南CSV(逗号分隔值)是一种通用的数据格式,用于在数据之间存储和交换信息。它的格式简单,易于使用,并且许多数据处理软件都支持CSV格式。通常,你可以使用电子表格软件(例如Microsoft Excel或Google Sheets)打开和编辑CSV文件,或使用编程语言(例如Python)处理CSV文件。

    2024-08-31
    24
  • 在ef中使用数据库上下文需要注意哪些事项_无法在源表中获得一组稳定的行

    在ef中使用数据库上下文需要注意哪些事项_无法在源表中获得一组稳定的行 using System; using System.Collections.Generic; using System.Data; using System.Data.Common; us…

    2023-03-23
    164
  • mysql水平拆分_MySQL多表查询

    mysql水平拆分_MySQL多表查询一、背景 老大安排要对某张大容量表进行分割,根据年份分割成多张表。 二、水平分割 水平拆分是指数据表行的拆分,表的行数超过百万行时,就会变慢,这时可以把一张的表的数据拆成多张表来存放。 定义规则分表后

    2022-12-26
    164
  • hog梯度特征提取python(hog特征提取代码)

    hog梯度特征提取python(hog特征提取代码)本文适合刚入门物体检测的人群学习,不涉及公式推理。

    2023-12-03
    126
  • Oracle——基本SQL「建议收藏」

    Oracle——基本SQL「建议收藏」 第 1 章 基本SQL SELECT语句 1. 对于日期型数据, 做 , / 运算不合法 2. 包含空值的数学表达式的值都为空值 3. 别名使用双引号! 4. oracle 中连接字符串使用

    2023-02-20
    175
  • hbase-site_hbase scan 查询过程

    hbase-site_hbase scan 查询过程前言: 对于任意一个系统而言,做好监控都是非常重要的,HBase也不例外。经常,我们会从JMX中获取相关指标来做展示、对HBase进行监控,那这些指标是怎么生成的呢?如果你想自定义自己的监控指标又该怎

    2023-02-15
    155
  • Python工程师:解析tempstr

    Python工程师:解析tempstr作为一名Python工程师,我们时常需要处理大量的数据,其中常用的一种数据格式就是字符串。而在字符串处理中,使用正则表达式是一种非常高效和灵活的方式,而正则表达式的一个关键就是:解析字符串。在这篇文章中,我们将会介绍如何使用Python来解析字符串,并针对不同场景进行实例演示。

    2024-04-16
    83
  • Python Keyed Definition: 定义Python键名的作用

    Python Keyed Definition: 定义Python键名的作用在Python中,可以使用键名来定义变量,这是一种非常方便的方法。例如,定义一个名为my_dict的字典,可以在定义字典的同时,使用键名来给它赋值

    2024-03-19
    87

发表回复

您的电子邮箱地址不会被公开。 必填项已用*标注