【是什么】
过滤器是JavaWeb三大组件之一,filter技术是Servlet2.3新增加的功能,新增加的许多功能中最重要的就是filter功能,java中的filter并不是一个标准的servlet,它不能处理用户请求,也不能对客户端生成响应,它主要是用来拦截请求的。主要用于在request到达servlet之前对其进行预处理,也可以在response离开servlet时对其进行后处理,是个典型的处理链。
【作用】
①在HttpservletRequest到达servlet之前,拦截客户的HttpServletRequest。
②根据需要检查HttpServletRequest,也可以修改HttpServletRequest头和数据
③在HttpServletResponse到达客户端之前,拦截 HttpServletResponse。
④根据需要检查HttpServletResponse,可以修改HttpServletResponse头和数据。
【优点】
执行过程中任何时候都可以打断,只要不执行doFilter()就不会再执行后面的过滤器和请求的内容。而实际使用时,特别注意过滤链的执行顺序问题。
【生命周期】
始于init(),陷于doFilter(),终于destroy()。从tomcat服务器启动时就开始执行init()方法。
【相关配置代码】
1.写Filter代码必须实现javax.servlet.Filter。Filter主要有三个方法,以设置字符集为例:
package com.bjpowernode.drp.util.filter;
import java.io.IOException;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
/**
* 采用filter统一处理字符集
*
* @author 郑艳霞
*
*/
public class CharsetEncodingFilter implements Filter {
@Override
public void destroy() {
}
@Override
public void doFilter(ServletRequest request, ServletResponse response,
FilterChain chain) throws IOException, ServletException {
System.out.println("CharsetEncodingFilter--开始--");
// 设置字符集
request.setCharacterEncoding("GB18030");
// 继续往下执行(有其他过滤直接执行过滤,否则执行jsp)
chain.doFilter(request, response);
System.out.println("CharsetEncodingFilter--结束--");
}
// 初始化参数信息
@Override
public void init(FilterConfig filterConfig) throws ServletException {
}
}
2.Web.xml配置
web.xml中,url_pattern的四种匹配规则
<span style="font-size:18px;"><?xml version="1.0" encoding="UTF-8"?>
<web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">
<filter>
<filter-name>CharsetEncodingFilter</filter-name>
<filter-class>com.bjpowernode.drp.util.filter.CharsetEncodingFilter</filter-class>
</filter>
<!-- 第一种:精确匹配,以“/”开头,加上servlet名称 -->
<filter-mapping>
<filter-name>CharsetEncodingFilter</filter-name>
<url-pattern>/servlet/TestServlet</url-pattern>
</filter-mapping>
<!-- 第二种:扩展匹配,由星号“*”和扩展名组成 -->
<filter-mapping>
<filter-name>CharsetEncodingFilter</filter-name>
<url-pattern>*.jsp</url-pattern>
</filter-mapping>
<!-- 第三种:路径前缀匹配,包含一个目录和一个/* -->
<filter-mapping>
<filter-name>CharsetEncodingFilter</filter-name>
<url-pattern>/sysmgr/*</url-pattern>
</filter-mapping>
<!-- 第四种:路径全部匹配,一般使用/* -->
<filter-mapping>
<filter-name>CharsetEncodingFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
</web-app>
</span>
任选一种方式,因为字符集设置是所有的页面都要设置的,所以就直接选择第二种啦。
【运行效果】
以添加用户为例,加入过滤器之后的执行过程简图如下:
在每一层加入打印信息,打印信息如下:
【小结】
过滤器远不止这么简单,一个项目中可以设置多个过滤器,除了字符集过滤,也可以有权限过滤等等。过滤器还可以进一步抽象,例如在CharsetEncodingFilter类中设置字符集类型,可以直接抽象到web.xml中进行设置,在CharsetEncodingFilter类调用init()方法初始化时直接获取等等。过滤器还可以进行请求判断和响应,例如访问服务器太过频繁,解决该问题可以将一些页面缓存,当有一类返回相同页面的请求到底过滤器时,可以直接拦截并且直接返回缓存中的页面等等。
还有很多需要我们研究学习的应用,加油吧