过滤器Filter讲解-以及两种配置方式

159 阅读3分钟

文章目录

1. 担任的角色

拦截请求、响应的作用 — 像小区的保安

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-GLU91ksd-1572973468884)(en-resource://database/8561:1)]

2. 运行的流程

请求的预处理: 改变客户端请求的内容
响应的后处理: 改变Servlet、JSP等给用户的响应内容

作用功能: 设置用户访问权限、记录用户操作、对请求进行编码、压缩给客户端响应的资源

由上面的过滤器流程可知、一个服务器可能设置了多个过滤器,但一个请求并不需要经过一个服务器的所有过滤器,每个过滤器都有自己的过滤条件来进行请求过滤

3. 生命周期

4. 三大过滤器核心接口

4.1 Filter接口

4.2 FilterConfig接口

4.3 FilterChain接口

5. 过滤器的使用

5.1 代码实现

public class TestFilter implements Filter{
	
   public TestFilter() {
        System.out.println("实例化对象TestFilter()");
   }
   
   @Override
	public void init(FilterConfig fc) throws ServletException {
		System.out.println("初始化过滤器init(FilterConfig)");
        		//过滤器的配置参数在下面文章中
        String name = fc.getFilterName();
        String user = fc.getInitParameter("user");
        String Year = fc.getInitParameter("Year");
        String ParameterNames = Collections.list( fc.getInitParameterNames() ).toString();
        System.out.println(name + "\n" + user + "\n" + ParameterNames);
		Filter.super.init(fc);
	}

	@Override
	public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
		
		System.out.println("过滤操作doFilter(req, resp, FilterChain)");
		 // 传给下一个过滤器,如果没有过滤器匹配,则直接访问资源
		chain.doFilter(request, response);
		
	}
	
   @Override
	public void destroy() {
		System.out.println("销毁过滤器destory()");
		Filter.super.destroy();
	}

}


运行结果

Totmcat服务器启动时:输出
	实例化对象TestFilter(
	初始化过滤器init(FilterConfig)
    TestFilter1
    小明
    2019
    [year, user]
   
每次有向服务器请示时:输出
	过滤操作doFilter(req, resp, FilterChain)
	
Tomcat服务器关闭时:输出
	销毁过滤器destory()

5.2 声明配置

过滤器匹配的URL:urlPatterns + servletName( 注意这里是servletName不是servlet-class )

5.2.1 注解@WebFilter

urlPattern:*星号 只能是路径 或 文件类型匹配,不可以两者结合

  1. 路径匹配: http://localhost:8080/*
  2. 文件类型匹配: *.html
  3. 不可以: /*.html 或者 http://localhost:8080/*.jsp 等等


注解示例

@WebFilter(
           urlPatterns = {"/index.jsp", "/login.jsp"},
           servletNames = { "TestServlet", "TestServlet2" },
           filterName = "TestFilter1",
           displayName = "TestFilter2",
           description = "TestFilter3",
           initParams = { 
                     @WebInitParam(name="user", value="小明"), 
                     @WebInitParam(name="year", value="2019")
           }
           dispatcherTypes = { DispatcherType.REUQEST, DispatcherType.FORWARD },
           asyncSupported = true           
)

5.2.2 配置文件web.xml
<servlet>
           <servlet-name>TestServlet</servlet-name>
           <servlet-class>top.linruchang.testServlet.TestServlet</servlet-class>
</servlet>
<servlet-mapping>
           <servlet-name>TestServlet</servlet-name>
           <url-pattern>/test1.do</url-pattern>
</servlet-mapping>

<filter>
		<filter-name>TestFilter</filter-name>
		<filter-class>top.linruchang.Filter.TestFilter</filter-class>
		<init-param>
			    <param-name>user</param-name>
			    <param-value>小明</param-value>
		</init-param>
		<init-param>
			    <param-name>year</param-name>
			    <param-value>2019</param-value>
		</init-param>
</filter>
<filter-mapping>
		<filter-name>TestFilter1</filter-name>
		<url-pattern>*.jsp</url-pattern>
		<servlet-name>TestServlet</servlet-name>
		<dispatcher>REQUEST</dispatcher>
</filter-mapping>

6. 过滤器的应用场景

6.1 设置请求、响应报文的编码

不必在每个Servlet类中,每次都需要将request、response进行转码

@WebFilter(
    urlPatterns = { "/*" }
)
class  F_CharacterFilter implements Filter {
    private static String charset = "utf-8";
    
    @Override
    public void init(FilterConfig filterConfig) throws ServletException {	
            String charset = filterConfig.getInitParameter("charset");
            if(charset!=null && charset=="") 
                TestFilter.charset = charset;
    }	

    @Override
    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {	
            request.setCharacterEncoding(charset);
            response.setCharacterEncoding(charset);
            chain.doFilter(request, response);
	}

	@Override
	public void destroy() {
	
	}
 
}

6.2 控制用户权限 - 思路

过滤器判断当前请求会话中是否存在 有关用户信息的域属性,用这个域属性进行权限的控制