Filter&Listener
# Filter
概述:Filter 表示过滤器,是 JavaWeb 三大组件(Servlet、Filter、Listener)之一。
过滤器可以将请求拦截下来,进行一些处理。
**作用:**通过过滤器完成一些通用的操作,如:request请求的编码设置。
# 开发步骤
- 定义类实现Filter接口,并重写其所有方法
- 配置Filter拦截资源的路径:在类上定义
@WebFilter注解。value属性值/*表示拦截所有资源 - 在doFilter方法中输出一句话并放行
示例
@WebFilter(filterName = "EncodingFilter", urlPatterns = "/*")
public class EncodingFilter implements Filter {
@Override
public void init(FilterConfig config) throws ServletException {}
@Override
public void doFilter(ServletRequest req, ServletResponse resp, FilterChain chain) throws ServletException, IOException {
// 因为ServletRequest是顶级接口,需要向下转型
HttpServletRequest request = (HttpServletRequest) req;
String method = request.getMethod();
if ("POST".equals(method)){
request.setCharacterEncoding("UTF-8");
}
// 放行
chain.doFilter(req, resp);
}
@Override
public void destroy() {}
}
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
chain.doFilter(request,response);就是放行,也就是让其访问本该访问的资源。init()方法会在服务器启动的时候调用,destroy()方法会在服务器正常关闭时调用 注意:Servlet4.0之后只需要重写doFilter()方法就可以了
放行部分资源请求
@WebFilter(filterName = "LoginFilter", urlPatterns = "/*")
public class LoginFilter implements Filter {
@Override
public void init(FilterConfig config) throws ServletException {
}
@Override
public void doFilter(ServletRequest req, ServletResponse resp, FilterChain chain) throws ServletException, IOException {
HttpServletRequest request = (HttpServletRequest) req;
// 存放直接放行的请求资源路径
String[] urls = {"loginServlet","registerServlet","checkCodeServlet","css","imgs","login.jsp","register.jsp"};
// 获取请求路径
String uri = request.getRequestURI();
for (String url : urls) {
// 符合则放行
if (uri.contains(url)) {
chain.doFilter(req,resp);
}
}
HttpSession session = request.getSession();
String username = (String) session.getAttribute("username");
if (username==null){
request.setAttribute("login_msg","请先登录");
request.getRequestDispatcher("login.jsp").forward(req,resp);
}else {
chain.doFilter(req, resp);
}
}
@Override
public void destroy() {
}
}
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
Filter执行流程
执行放行前逻辑->放行->访问资源->放行后逻辑->响应数据
public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
System.out.println("放行前...");
// 放行
chain.doFilter(request,response);
System.out.println("放行后...")
}
2
3
4
5
6
注意:即使访问的资源不存在,也会执行过滤器
# Filter拦截路径设置
拦截路径表示Filter会对请求的哪些资源进行拦截,使用通过配置注解@WebFilter("拦截路径")
拦截路径有如下四种配置方式:
- 拦截具体的资源:
/index.jsp:只有访问index.jsp时才会被拦截 - 目录拦截:
/user/*:访问/user下的所有资源,都会被拦截 - 后缀名拦截:
*.jsp:访问后缀名为jsp的资源,都会被拦截 - 拦截所有:
/*:访问所有资源,都会被拦截
# Filter拦截行为
- Filter 过滤器默认拦截的是请求,在实际开发中,还有请求转发。请求转发默认过滤器不拦截。
- 常用过滤器拦截行为类型介绍
| 过滤器拦截行为类型 | 作用 |
|---|---|
| REQUEST | 只拦截直接的请求,默认的拦截行为类型 注:一次重定向则前后相当于发起了两次请求,所以2次都会拦截过滤 |
| FORWARD | 只拦截过滤“请求转发”的请求 |
拦截行为的注解修改方式
| @WebFilter注解属性 | 说明 |
|---|---|
| dispatcherTypes = {DispatcherType.REQUEST} | 拦截请求行为,默认行为 |
| dispatcherTypes = {DispatcherType.FORWARD} | 拦截请求转发,注意:如果只配置这种方式,只会拦截请求转发,不会拦截请求 |
| dispatcherTypes = { DispatcherType.REQUEST, DispatcherType.FORWARD } | 设置采用拦截请求和请求转发两种行为 |
@WebFilter(urlPatterns = "/*",dispatcherTypes = {DispatcherType.REQUEST,DispatcherType.FORWARD})
# 过滤器链
**概述:**过滤器链是指在一个Web应用,可以配置多个过滤器,这多个过滤器称为过滤器链。

执行流程:
- 执行
Filter1的放行前逻辑代码 - 执行
Filter1的放行代码 - 执行
Filter2的放行前逻辑代码 - 执行
Filter2的放行代码 - 访问到资源
- 执行
Filter2的放行后逻辑代码 - 执行
Filter1的放行后逻辑代码
注意:使用注解配置Filter,调用浏览器的优先级是按照过滤器类名(字符串)的自然排序 例:
BFilterDemo和AFilterDemo。AFilterDemo过滤器先执行。
# XML配置Filter
在web.xml中配置
<!--给过滤器起名字-->
<filter>
<filter-name>demo1Filter</filter-name>
<filter-class>cn.kk.Servlet.demoFilter</filter-class>
</filter>
<!-配置过滤器的拦截路径-->
<filter-mapping>
<filter-name>demo1Filter</filter-name>
<url-pattern>/demo</url-pattern>
</filter-mapping
2
3
4
5
6
7
8
9
10
XML配置的过滤器链,按照配置的先后顺序执行,从上到下 注解和xml配置共存的情况下,xml配置的优先级更高
# Listener
概述
- Listener表示监听器,是JavaWeb三大组件(Servlet、Filter、Listener)之一。
- 监听器可以监听就是在
application,session,request三个对象创建、销毁或者往其中添加修改删除属性时自动执行代码的功能组件。
application是ServletContext类型的对象,ServletContext代表整个Web应用,在服务器启动时Tomcat会自动创建该对象,在服务器关闭时会自动销毁该对象
# 监听器分类
Javaweb提供了8个监听器:
ServletContextListener这个监视器会比较常接触,ServletContextListener是用来监听 ServletContext 对象的创建和销毁的。
ServletContextListener的方法
| 方法 | 说明 |
|---|---|
| void contextInitialized(ServletContextEvent sce) | ServletContext 对象被创建了会自动执行的方法 |
| void contextDestroyed(ServletContextEvent sce) | ServletContext 对象被销毁时会自动执行的方法 |
ServletContextListenerAttributeListener中的getValue()方法获取的值都是事件发生前的值
使用场景
- Spring框架在启动时会创建很多对象
- 电商网站定时扫描,服务器启动后每隔两分钟清除超时订单