过滤器Filter
文章目录
- 过滤器Filter
- 一、过滤器简介
- 1.定义
- 2.作用
- 3.拦截原理
- 4.常用方法:
- 5.Filter的生命周期
- 4.web.xml中配置
- 5.@WebFilter
一、过滤器简介
1.定义
过滤器是对Web应用程序的请求和响应添加功能的Web服务组件(实现 javax.servlet.Filter 接口的 Java 类。)
调用web资源之前添加功能;
//定义了一个MyFilter过滤器
public class MyFilter implements Filter{
}
Filter 过滤器它是 JavaWeb 的三大组件之一。三大组件分别是:Servlet 程序、Listener 监听器、Filter 过滤器
2.作用
- 检查请求并执行相应的行动,并阻塞请求或响应,使其不能进一步传递。
- 修改请求和响应的头部和数据,用户可以提供自定义的请求或可以通过提供定制的响应版本来实现。
- 可被添加到Web应用程序中或者从Web应用程序中删除而不需重写基层应用程序代码,并能向过去的代码中添加新功能。
- 在实际开发中,譬如我们可以对客户提交的数据进行重新编码,可以从系统获得配置信息,可以过滤客户提交的某些不合法的词汇,可以验证客户是否已经登录,可以验证客户端浏览器是否支持当前的应用,还可以记录系统的日志文件等等。
3.拦截原理
Filter接口中有一个doFilter方法,当我们编写好Filter,并配置对哪个web资源进行拦截后,WEB服务器每次在调用web资源的service方法之前,都会先调用一下filter的doFilter方法。(调用web资源之前先调用过滤器的doFilter())
web服务器在调用doFilter方法时,会传递一个filterChain对象进来,filterChain对象也提供了一个doFilter方法,开发人员可以根据需求决定是否调用此方法。调用filterChian对象的doFilter方法,web服务器会检查FilterChain对象中是否还有filter,如果有,则调用第2个filter,如果没有,则调用目标资源。相反,如果不调用该方法,web资源不会被访问。 (filterChian.doFIlter()调用目标资源)
4.常用方法:
-
初始化:init(FilterConfig filterConfig)
-
过滤doFilter(ServletRequest req, ServletResponse resp, FilterChainfilterChain):Filter中的doFilter()方法主要写实现过滤器功能的代码,doFillter方法中可以一句需求决定是否调用filterChain的doFilter方法放行
过滤器预处理完之后,是否放行进行下一步,调用filterChain的doFilter方法放行;
-
注销过滤器:destroy()
5.Filter的生命周期
实例化>>初始化>>过滤>>销毁;
- 实例化: web程序启动创建Filter对象,
- 初始化init(): 实例对象调用init()方法,完成初始化
- 过滤doFilter(): 所有请求都会调用doFilter()执行过滤的代码块
- 销毁doDetroy()
- web应用程序启动时,web 服务器将创建Filter 的实例对象,并调用其init方法,完成对象的初始化功能,从而为后续的用户请求作好拦截的准备工作,filter对象只会创建一次,init方法也只会执行一次。
- 所有的请求都会经过过滤器,并多少调用doFilter()方法
- 过滤器的注销会随着服务器的关闭而关闭。除此之外,Web容器还可以通过调用destroy方法销毁Filter。destroy方法在Filter的生命周期中仅执行一次。在destroy方法中,可以释放过滤器使用的资源。
4.web.xml中配置
<!--过滤器映射-->
<!--过滤器名字,过滤器实现类-->
<filter>
<filter-name>session</filter-name>
<filter-class> </filter-class>
</filter>
<!--指定过滤器映射的路径-->
<filter-mapping>
<filter-name>session</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
<!--可以使用注解@WebFilter替代标签属性-->
5.@WebFilter
@WebFilter 用于将一个类声明为过滤器,该注解将会在部署时被容器处理,容器将根据具体的属性配置将相应的类部署为过滤器。该注解具有下表给出的一些常用属性 ( 以下所有属性均为可选属性,但是 value、urlPatterns、servletNames 三者必需至少包含一个,且 value 和 urlPatterns 不能共存,如果同时指定,通常忽略 value 的取值 ):
@WebFilter("/*")//过滤器的截点,根路径下的所有包内容
public class HrFilter implements Filter {//实现Filter接口
@Override
public void init(FilterConfig filterConfig) throws ServletException {
}
@Override
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
// 调用根路径下的servlet资源先调用dofilter()方法
request.setCharacterEncoding("utf-8");
response.setCharacterEncoding("utf-8");
HttpServletRequest httpServletRequest = (HttpServletRequest) request;
HttpServletResponse httpServletResponse = (HttpServletResponse) response;
//login方法时已经定义session一次会话的对象hr,每个方法调用时都有session
Object hr = httpServletRequest.getSession().getAttribute("hr");
String requestURI = httpServletRequest.getRequestURI();
//打开login.jsp页面,在提交登录时,先进性filter验证,再执行servlet程序,登陆时与hr无关只验证登录路径
//打开页面时,路径是:...../login.jsp,则继续进行调用目标资源hrServlet的login方法
//之后每次调用hrServlet方法都先走过滤器,因为login方法已经设置会话session的hr指,会话结束前一直有hr
//即便跳转页面hr也在,所以调用其他方法时,hr不为null
if (requestURI.contains("login") || hr != null) {
//调用过滤器之后再继续调用目标资源
chain.doFilter(request, response);
} else {
httpServletResponse.sendRedirect("/hrms/login.jsp");
}
}
@Override
public void destroy() {
}
}
endRedirect(“/hrms/login.jsp”);
}
}
@Override
public void destroy() {
}
}