什么是Filter(过滤器)?

什么是Filter(过滤器)?

​ Filter也称之为过滤器,它是Servlet技术中最实用的技术,Web开发人员通过Filter技术,对web服务器管理的所有web资源:例如Jsp, Servlet, 静态图片文件或静态 html 文件等进行拦截,从而实现一些特殊的功能。例如实现URL级别的权限访问控制、过滤敏感词汇、压缩响应信息等一些高级功能。

它主要用于对用户请求进行预处理,也可以对HttpServletResponse进行后处理。使用Filter的完整流程:Filter对用户请求进行预处理,接着将请求交给Servlet进行处理并生成响应,最后Filter再对服务器响应进行后处理。

过滤器原理

​ 当我们使用过滤器时,过滤器会对游览器的请求进行过滤,过滤器可以动态的分为3个部分,1.放行之前的代码,2.放行,3.放行后的代码,这3个部分分别会发挥不同作用。

第一部分代码会对游览器请求进行第一次过滤,然后继续执行

第二部分代码就是将游览器请求放行,如果还有过滤器,那么就继续交给下一个过滤器

第三部分代码就是对返回的Web资源再次进行过滤处理
我们使用过滤器,也就是说,不止请求会经过过滤器,我们的响应也会经过过滤器。

创建过滤器(Filter)

​ 1.先书写一个普通类,如果普通类实现了Filter接口,则此类为过滤器类

		public class Filter1 implements Filte
  1. 让普通类实现接口中的抽象方法,然后决定是否放行

    package com.bjpowernode.filter;
    
    import javax.servlet.*;
    import java.io.IOException;
    
    public class Filter1 implements Filter {
    
        @Override
        public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
           
        }
    
    }
    
    

Filter接口有3个方法,但是这里我们值实现一个,我们实现了一个doFilter方法,这个方法就是我们写过滤代码的地方,(另外两个我们会在生命周期里面讲解)

3.在web.xml文件配置过滤器的过滤路径或者通过注解方式配置(Filter的两种配置方式)

3.1注解方式

如果我们使用注解方式的话需要先了解属性,那么我们来先看一下源码

//
// Source code recreated from a .class file by IntelliJ IDEA
// (powered by Fernflower decompiler)
//

package javax.servlet.annotation;

import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import javax.servlet.DispatcherType;

@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface WebFilter {
    String description() default "";

    String displayName() default "";

    WebInitParam[] initParams() default {};

    String filterName() default "";

    String smallIcon() default "";

    String largeIcon() default "";

    String[] servletNames() default {};

    String[] value() default {};

    String[] urlPatterns() default {};

    DispatcherType[] dispatcherTypes() default {DispatcherType.REQUEST};

    boolean asyncSupported() default false;
}

里面的配置还是很多的,这里我们只讲解我们需要使用的

filterName:该filter的名字
initParams:初始化参数
displayName:filter显示名称
servletNames:指定对哪些servlet进行过滤
asyncSupported:是否支持异步模式
urlPatterns:指定拦截路径
value:指定拦截路径 (urlPatterns和value是一样的。只能配置一个,两个都配置就会报错)

注解配置

@WebFilter("/*")   这里的(/*)表示过滤所有的,里面的多个参数用 **,** 进行分隔。

注意:如果我们仅仅需要配置一个拦截路径,那么我们可以直接简写@WebLister(“拦截路径”),如@WebFilter(“/*”)就是拦截所有请求。

3.2xml方式配置



        
            filter1
            com.bjpowernode.filter.Filter1 
        
    
        filter1
        /* 表示过滤所有的
    


​ 这个就是xml配置方式,里面属性都是一样的,这个和Servlet的配置方式基本一样,这里就不再赘述了。

使用过滤器(Filter)

​ 我们先来感受一下如何使用过滤器,其它细节我们后面会一 一讲解。

package com.bjpowernode.filter;

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

@WebFilter("/*") // 注解方式
public class Filter1 implements Filter {

    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
        System.out.println("对request进行过滤");
        filterChain.doFilter(servletRequest,servletResponse);  // 放行
        System.out.println("对request完成过滤");
    }

}

然后 启动服务器,然后我们在游览器中输入

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-CFqohHGR-1667654438454)(C:\Users\ADMINI~1\AppData\Local\Temp\1667648186406.png)]

注意:上面之所以出现这个页面是因为我们服务器下面没有资源。

然后我们打开后台你会看到如下图

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-FjL0XkeO-1667654438457)(C:\Users\ADMINI~1\AppData\Local\Temp\1667648386995.png)]

从上面的执行结果来看,我们此时就可以得出结论,过滤器是不会管资源是否存在的,而只会对配置的拦截路径进行拦截

1.1 Fliter(过滤器)的生命周期

同servlet对象一样,Filter对象的创建也是交给web服务器完成的,在web服务器创建和使用及最后销毁filter时,会调用filter对应的方法

初始化方法:

public void init(FilterConfig filterConfig);

和我们编写的Servlet程序一样,Filter的创建和销毁由WEB服务器负责。 web 应用程序启动时,web 服务器将创建Filter 的实例对象,并调用其init方法,读取web.xml配置,完成对象的初始化功能,从而为后续的用户请求作好拦截的准备工作(filter对象只会创建一次,init方法也只会执行一次)。开发人员通过init方法的参数,可获得代表当前filter配置信息的FilterConfig对象。

拦截请求方法

public void doFilter

这个方法完成实际的过滤操作。当客户请求访问与过滤器关联的URL的时候,Servlet过滤器将先执行doFilter方法。FilterChain参数用于访问后续过滤器。

销毁方法***

public void destroy();

Filter对象创建后会驻留在内存,当web应用移除或服务器停止时才销毁。在Web容器卸载 Filter 对象之前被调用。该方法在Filter的生命周期中仅执行一次。在这个方法中,可以释放过滤器使用的资源。

生命周期三个阶段的小小总结

Filter有3个阶段,分别是初始化,拦截和过滤,销毁。

1.初始化阶段:当服务器启动时,我们的服务器(Tomcat)就会读取配置文件,扫描注解,然后来创建我们的Filter。

2.拦截和过滤阶段:只要请求资源的路径和拦截的路径相同,那么过滤器就会对请求进行过滤,这个阶段在服务器运行过程中会一直循 环。
3.销毁阶段:当服务器(Tomcat)关闭时,服务器创建的Filter也会随之销毁。

代码演示

package com.bjpowernode.filter;

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

@WebFilter("/*") // 注解方式
public class Filter1 implements Filter {
  /*
    * 1. Filter的创建时机是 服务器启动的时候
    * 2. init方法只调用一次,并紧跟构造器方法调用之后
    * 3. doFilter 方法,每次请求都会进入 该方法 ,并且 是在调用service之前,能不能进入service 方法,就要看 doFilter 方法有没有放行
    * 4. destroy 方法,在服务器正常关闭的请情况下,调用
    *
    * */
    // 构造器
   public Filter1 (){
       System.out.println("我是构造器!");
    }
    @Override
    public void init(FilterConfig filterConfig) throws ServletException {
        System.out.println("init()"); // 这个是初始化方法,在服务器启动的时候就会执行

    }

    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
        //这个方法就是过滤和拦截的方法,当请求和拦截匹配时调用
        System.out.println("doFilter");

    }

    @Override
    public void destroy() {
       // 这个方法是销毁方法,只有在项目正常关闭的情况下才会执行
        System.out.println("destroy");

    }
}

启动服务器后台输出

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-v5HzRUK1-1667654438458)(C:\Users\ADMINI~1\AppData\Local\Temp\1667650406113.png)]

游览器访问

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-S2AC4LPr-1667654438460)(C:\Users\ADMINI~1\AppData\Local\Temp\1667650534079.png)]

游览器访问过后后台输出

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-oREeEfgt-1667654438461)(C:\Users\ADMINI~1\AppData\Local\Temp\1667650587412.png)]

在这里我们可以得出结论

在服务器启动的时候过滤器的构造器会执行,随后init()方法会执行,并且这他们两个只会在服务器启动的时候执行一次

然后我们再次通过游览器访问

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-FjpK8P1v-1667654438462)(C:\Users\ADMINI~1\AppData\Local\Temp\1667650862167.png)]

后台输出

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-cGj1IFQk-1667654438464)(C:\Users\ADMINI~1\AppData\Local\Temp\1667650911939.png)]

在这里我们又得到一个结论

doFilter方法只会在每次有人访问的时候执行

关闭服务器后台输出

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-9jJZErgh-1667654438465)(C:\Users\ADMINI~1\AppData\Local\Temp\1667651073758.png)]

执行的结果都和我们预想的一样,这也就验证了我们上面所学生命周期结果是相吻合的了。

FilterConfig

FilterConfig 类见名知义, 它是 Filter 过滤器的配置文件类。
Tomcat 每次创建 Filter 的时候, 也会同时创建一个 FilterConfig 类, 这里包含了 Filter 配置文件的配置信息。
FilterConfig 类的作用是获取 filter 过滤器的配置内容
1、 获取 Filter 的名称 filter-name 的内容
2、 获取在 Filter 中配置的 init-param 初始化参数
3、 获取 ServletContext 对象

FilterConfig的四个方法

  • getFilterName():获取filter的名称
  • getServletContext():获取ServletContext
  • getInitparamter(String var1):获取配置的初始参数的值
  • getInitParamterNames():获取配置的所有参数名称

FilterConfig实例运用

代码实列

package com.bjpowernode.filter;

import javax.servlet.*;
import java.io.IOException;
import java.util.Enumeration;
 
public class FilterConfig1 implements Filter {
 
    @Override
    public void init(FilterConfig filterConfig) throws ServletException {
        Enumeration names = filterConfig.getInitParameterNames(); //getInitParameterNames()得到所有配置参数的的名称
       // 遍历出所有的参数信息并打印到控制台
        while (names.hasMoreElements()) {
            String name = names.nextElement();
            System.out.println(name+" = "+filterConfig.getInitParameter(name));
        }
    }

    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
    }

    @Override
    public void destroy() {
    }
}

xml文件配置信息



         <--这是前面测试用的不用管注释而已-->
        
		
        
                myFilterConfig
                com.bjpowernode.filter.FilterConfig1
                
                        driver
                        com.mysql.jdbc.Driver
                
                
                        url
                        jdbc:mysql://localhost:3306/web
                
                
                        username
                        root
                
                
                        password
                        123456
                
        
        
                myFilterConfig
                /*
        

启动服务器输出结果如下图所示

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-0llKxuNM-1667654438466)(C:\Users\ADMINI~1\AppData\Local\Temp\1667653718879.png)]

FilterConfig读取配置文件演示完毕。

关于过滤器的讲解到这里就结束了,当然这上面讲的也很多不足之处,关于过滤器更多的知识点各位在另行查阅相关的文章

谢谢你的阅读!

56



myFilterConfig
/*


启动服务器输出结果如下图所示

[外链图片转存中...(img-0llKxuNM-1667654438466)]

FilterConfig读取配置文件演示完毕。

关于过滤器的讲解到这里就结束了,当然这上面讲的也很多不足之处,关于过滤器更多的知识点各位在另行查阅相关的文章
写的不好还请大佬们谅解

谢谢你的阅读!



你可能感兴趣的:(java,servlet)