1、Filter过滤器
Filter也称之为过滤器,它是Servlet技术中最实用的技术,WEB开发人员通过Filter技术,对web服务器管理的所有web资源:例如Jsp, Servlet, 静态图片文件或静态 html 文件等进行拦截,从而实现一些特殊的功能。例如实现URL级别的权限访问控制、过滤敏感词汇、压缩响应信息等一些高级功能。
Servlet三大技术
- Servlet 动态资源
- Filter 过滤器
- Listener 监听器
Filter实际开发中的作用
1.简单一点的 设置字符集
2.用户的权限验证
3.控制Session的开关
4.知名的Struts2的核心技术就是基于Filter开发的
2、Filter的生命周期
1、init():该方法在服务器启动时运行. Filter对象随着服务器 的启动而创建
2、doFilter():当需要拦截时 该方法运行
3、destroy():服务器关闭时调用,FIlter对象随着服务器的关闭而销毁
public class MyFilter implements Filter {
// 当web应用程序启动时
public void init(FilterConfig fConfig) throws ServletException {
System.out.println("filter init()");
}
// 当web应用销毁时调用
public void destroy() {
System.out.println("filter destory()-------------");
}
// 当访问servlet时调用
public void doFilter(ServletRequest request, ServletResponse response,
FilterChain chain) throws IOException, ServletException {
System.out.println("filter doFilter() before---------------");
chain.doFilter(request, response);
System.out.println("filter doFilter() after-----------------");
}
}
在web.xml中的配置如下
<filter>
<display-name>MyFilter</display-name>
<filter-name>MyFilter</filter-name>
<filter-class>com.example.filter.MyFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>MyFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
Filter中FilterConfig对象常用的几个方法
1、String getFilterName()获得FIlter注册的名称
2、String getInitParameter(String name) 根据键获得FIlter元素中的 键值对
3、Enumeration getInitParameterNames() 获得所有Filter元素中的键.
4、ServletContext getServletContext() 获得ServletContext(application)对象
FilterChain
FilterChain就是在请求时,服务器会把所有要经过的FIlter实例引用交给FilterChain. 我们在Filter的doFilter方法中可以拿到该对象,并且调用该对象的doFilter方法(放行),filterchain会去向下找后续要调用的过滤器.如果有就继续调用下一个过滤器的doFilter方法。
3、Filter配置
如果有多个filter,哪个Mapping路径配置在前面就先调用哪个。
FIlter的路径配置方式有两种
方式1
/* 按照配置的路径来拦截.
方式2:
AServlet 按照访问的Servlet来拦截(不常用)
Filter配置中的拦截方式
子元素可以设置的值及其意义:
REQUEST:当用户直接访问页面时,Web容器将会调用过滤器。如果目标资源是通过RequestDispatcher的include()或forward()方法访问时,那么该过滤器就不会被调用。
INCLUDE:如果目标资源是通过RequestDispatcher的include()方法访问时,那么该过滤器将被调用。除此之外,该过滤器不会被调用。
FORWARD:如果目标资源是通过RequestDispatcher的forward()方法访问时,那么该过滤器将被调用,除此之外,该过滤器不会被调用。
ERROR:如果目标资源是通过声明式异常处理机制调用时,那么该过滤器将被调用。除此之外,过滤器不会被调用。
登陆权限的设置
public class AFilter implements Filter {
public AFilter() {
// TODO Auto-generated constructor stub
}
public void destroy() {
// TODO Auto-generated method stub
}
public void doFilter(ServletRequest request, ServletResponse response,
FilterChain chain) throws IOException, ServletException {
HttpServletRequest req = (HttpServletRequest) request;
HttpServletResponse resp = (HttpServletResponse) response;
// 1.获得用户访问的路径
String path = req.getServletPath();
// 2.判断访问的路径是否属于 不需要登录 的资源
// 如果是login.jsp 通过 // "/login.jsp" "/LoginServlet"
if (path.equals("/login.jsp") || path.equals("/LoginServlet")) {
chain.doFilter(request, response);
return;
} else {
// 3. 如果缓存中没有登陆,进入到登陆界面
String name = (String) req.getSession().getAttribute("user");
if (name == null) {
resp.sendRedirect(req.getContextPath() + "/login.jsp");
return;
} else {
// 4.判断当前访问资源是否 需要权限 "/admin/list.jsp"
if (path.contains("/user/")) {
// 不需要权限 => 放行
chain.doFilter(request, response);
return;
} else {
// 需要权限=>继续
// 5.判断是否有访问的权限
if (name.equals("admin")) {
// 有权限=>放行
chain.doFilter(request, response);
return;
} else {
// 没有权限=> 转发到报错页面,提示没有权限
req.getRequestDispatcher("/error.jsp").forward(request,
response);
}
}
}
}
}
public void init(FilterConfig fConfig) throws ServletException {
// TODO Auto-generated method stub
}
}