Filter入门与案例
2017-10-24 本文已影响18人
小小蒜头
简介:Filter也称之为过滤器,WEB开发人员通过Filter技术,对WEB服务器管理的所有WEB资源:例如JSP,SERVLET,静态图片文件或静态HTML文件等进行拦截,从而实现一些特殊的功能。例如实现URL级别的权限访问控制、过滤敏感词汇、压缩响应信息等一些高级功能。
![](https://img.haomeiwen.com/i1037735/73c450e015256a0a.png)
Filter在开发中的常见应用:
- Filter可以在目标资源执行之前,进行权限检查,检查用户有无权限,如有权限,则放行,如没有,则拒绝放行。
- Filter可以放行之前,对request和response进行预处理,从而实现一些全局性的设置。
- Filter放行之后,可以捕获到目标资源的输出,从而对输出作出类似于压缩这样的设置。
Filter生命周期:Filter在服务器启动时就已经创建,停止服务器或者移除WEB应用时会被摧毁。
Filter的部署——注册Filter
<filter>
<filter-name>testFilter</filter-name>
<filter-class>org.test.TestFilter</filter-class>
<init-param>
<param-name>word_file</param-name>
<param-value>/WEB-INF/word.txt</param-value>
</init-param>
</filter>
-
<filter-name>
用于为过滤器制定一个名字,该元素的内容不能为空 -
<filter-class>
用于指定过滤器的完整的限定类名 -
<init-param>
用于为过滤器指定初始化参数,它的子元素<param-name>
指定参数名字,<param-value>
指定参数值。在过滤器中,可以使用FilterConfig接口对象来访问初始化参数。
Filter的部署——映射Filter
REQUEST:当用户直接访问页面时,WEB容器将会调用过滤器。如果目标资源是通过RequestDispatcher的include()或forward()方法访问时,那么该过滤器就不会被调用。
INCLUDE:如果目标资源是通过RequestDispatcher的include()方法访问时,那么该过滤器将被调用。除此之外,该过滤器不会被调用。
FORWARD:如果目标资源是通过RequestDispatcher的forward()方法访问时,那么该过滤器将被调用。除此之外,该过滤器不会被调用。
ERROR:如果目标资源是通过声明式异常处理机制调用时,那么该过滤器将被调用。除此之外,该过滤器不会被调用。
-
<filter-mapping>
用于设置一个Filter所负责拦截的资源。一个Filter拦截的资源可通过两种方式来指定:Servlet名称和资源访问的请求路径。 -
<filter-name>
用于设置Filter的注册名称。该值必须是在<filter>元素中声明过的过滤器名称。 -
<url-pattern>
设置Filter所拦截的请求路径(过滤器关联的URL样式) -
<servlet-name>
指定过滤器所拦截的servlet名称。 -
< dispatcher>
指定过滤器所拦截的资源被servlet容器调用的方式,可以REQUEST,INCLUDE,FORWARD和ERROR之一,默认request。用户可以设置多个< dispatcher>子元素用来指定Filter对资源的多种调用方式进行拦截。
案例一:解决全站乱码
配置信息web.xml
<filter>
<filter-name>CharacterEncodingFilter</filter-name>
<filter-class>cn.itcast.filter.CharacterEncodingFilter</filter-class>
<init-param>
<param-name>charset</param-name>
<param-value>UTF-8</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>CharacterEncodingFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
具体代码:
private FilterConfig config;
private String defaultConfig = "UTF-8";//定义一个缺省的字符集
@Override
public void init(FilterConfig filterConfig) throws ServletException {
this.config = filterConfig;
}
@Override
public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
String charset = this.config.getInitParameter("charset");
if (charset == null) {
charset = defaultConfig;
}
HttpServletRequest request = (HttpServletRequest) servletRequest;
HttpServletResponse response = (HttpServletResponse) servletResponse;
request.setCharacterEncoding(charset);
response.setCharacterEncoding(charset);
response.setContentType("text/html;charset = " + charset);
filterChain.doFilter(request,response);
}
@Override
public void destroy() {
}
案例二:禁止浏览器缓存所有动态页面
配置信息web.xml
<filter>
<filter-name>NoCacheFilter</filter-name>
<filter-class>cn.itcast.filter.NoCacheFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>NoCacheFilter</filter-name>
<url-pattern>*.jsp</url-pattern>
</filter-mapping>
主要就是控制响应头,具体代码:
HttpServletRequest request = (HttpServletRequest) servletRequest;
HttpServletResponse response = (HttpServletResponse) servletResponse;
response.setDateHeader("Expires", -1);
response.setHeader("Cache-Control", "no-cache");
response.setHeader("Pragma", "no-cache");
filterChain.doFilter(request, response);
案例三:控制浏览器缓存页面中的静态资源
场景:有些动态页面中引用了一些图片或css文件以修饰页面效果,这些图片和css文件经常是不变化的,所以为减轻服务器的压力,可以使用Filter控制浏览器缓存这些文件,以提升服务器的性能。
配置信息web.xml
<filter>
<filter-name>CacheFilter</filter-name>
<filter-class>cn.itcast.filter.CacheFilter</filter-class>
<init-param>
<param-name>css</param-name>
<!-- 以分钟为单位 -->
<param-value>10</param-value>
</init-param>
<init-param>
<param-name>jpg</param-name>
<param-value>1</param-value>
</init-param>
<init-param>
<param-name>js</param-name>
<param-value>20</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>CacheFilter</filter-name>
<url-pattern>*.jpg</url-pattern>
</filter-mapping>
<filter-mapping>
<filter-name>CacheFilter</filter-name>
<url-pattern>*.css</url-pattern>
</filter-mapping>
<filter-mapping>
<filter-name>CacheFilter</filter-name>
<url-pattern>*.js</url-pattern>
</filter-mapping>
具体代码:
package cn.itcast.filter;
import com.sun.java.swing.plaf.windows.WindowsTreeUI;
import javax.servlet.*;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
/**
* Created by yvettee on 2017/10/24.
*/
public class CacheFilter implements Filter {
private FilterConfig config;
@Override
public void init(FilterConfig filterConfig) throws ServletException {
this.config = filterConfig;
}
@Override
public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
HttpServletRequest request = (HttpServletRequest) servletRequest;
HttpServletResponse response = (HttpServletResponse) servletResponse;
//1.获取用户想访问的资源
String uri = request.getRequestURI();
//2.获取该资源的访问时间
int expires = 0;
if (uri.endsWith(".jpg")) {
expires = Integer.parseInt(this.config.getInitParameter("jpg"));
} else if (uri.endsWith(".css")) {
expires = Integer.parseInt(this.config.getInitParameter("css"));
} else {
expires = Integer.parseInt(this.config.getInitParameter("js"));
}
response.setDateHeader("Expires", System.currentTimeMillis() + expires * 60 * 1000);
filterChain.doFilter(request, response);
}
@Override
public void destroy() {
}
}
源代码:https://github.com/yvettee36/FilterBase
下篇:http://www.jianshu.com/p/a0853749b8ed