Filter
概述
1、JavaWeb 三大组件:Servlet 程序、Listener 监听器、Filter 过滤器
2、JavaEE 规范,即接口
3、作用:拦截请求,过滤响应
4、拦截请求常见的应用场景
(1)事务管理
(2)权限检查
(3)日记操作
使用步骤
1、编写一个类实现 Filter 接口
2、实现过滤方法 doFilter()
3、web.xml 配置 Filter 拦截路径
生命周期
1、构造器方法 -> init() 初始化方法
(1)在 Web 工程启动时执行,Filter 已经创建
2、doFilter() 过滤方法
(1)每次拦截到请求,就会执行
3、destroy() 销毁方法
(1)停止 Web 工程时,就会执行,销毁 Filter 过滤器
FilterConfig 类
1、Filter 过滤器的配置文件类
2、Tomcat 每次创建 Filter 时,同时创建一个 FilterConfig 类,包含 Filter 配置文件的配置信息
3、作用:获取 Filter 过滤器的配置内容
(1)获取 Filter 名称 filter-name 的内容
public String getFilterName();
(2)获取在 Filter 中配置的 init-param 初始化参数
public String getInitParameter(String name);
public Enumeration<String> getInitParameterNames();
(3)获取 ServletContext 对象
public ServletContext getServletContext();
FilterChain 接口
1、过滤器链
2、只有一个方法
public void doFilter(ServletRequest request, ServletResponse response) throws IOException, ServletException;
(1)若有 Filter,则执行下一个 Filter 过滤器
(2)若没有 Filter,则执行目标资源
3、多个 Filter 执行特点
(1)所有 Filter、目标资源都默认执行在同一个线程中
(2)都共用同一个 Request 对象
(3)由 web.xml 中从上到下配置顺序,决定执行的优先顺序
拦截路径
1、精确匹配
(1)示例
<url-pattern>/target.jsp</url-pattern>
(2)表示请求地址必须为:http://ip:port/工程路径/target.jsp
2、目录匹配
(1)示例
<url-pattern>/admin/*</url-pattern>
(2)表示请求地址必须为:http://ip:port/工程路径/admin/*
3、后缀名匹配
<url-pattern>*.html</url-pattern>
(2)表示请求地址必须以 .html 结尾
4、Filter 只关心请求的地址是否匹配,不关心请求的资源是否存在
ThreadLocal 类
1、作用:解决多线程的数据安全问题
2、特点
(1)ThreadLocal 可以为当前线程关联一个数据,可以是普通变量、对象、数组、集合,可以像 Map 一样存取数据,key 为当前线程
(2)每一个 ThreadLocal 对象,只能为当前线程关联一个数据,如果要为当前线程关联多个数据,就需要使用多个 ThreadLocal 对象实例
(3)每个 ThreadLocal 对象实例定义时,一般都是 static 类型
(4)在 ThreadLocal 中保存数据,线程销毁后,由 JVM 自动释放
3、set() 源码
public void set(T value) {
Thread t = Thread.currentThread();//获取当前线程
ThreadLocalMap map = getMap(t);//每个线程维护各自的容器(ThreadLocalMap)
if (map != null)
map.set(this, value);//key对应ThreadLocal
else
createMap(t, value);//第一次添加数据,进行初始化
}
4、get() 源码
public T get() {
Thread t = Thread.currentThread();//获取当前线程
ThreadLocalMap map = getMap(t);//获取上个线程相关的ThreadLocalMap
if (map != null) {
ThreadLocalMap.Entry e = map.getEntry(this);//this表示ThreadLocal对象,定位工作纽带
if (e != null) {
@SuppressWarnings("unchecked")
T result = (T)e.value;//获取工具箱
return result;
}
}
return setInitialValue();
}
5、每次使用 ThreadLocal 后,手动调用 remove()
(1)删除对应的 value 对象,可以避免内存泄漏
Filter、ThreadLocal 组合管理事务
//开启事务
try {
filterChain.doFilter();
//提交事务
} catch (Exception e) {
//回滚事务
e.printStackTrace();
throw new RuntimeException(e);
}
1、使用 ThreadLocal 对象,确保所有操作都使用同一个 Connection 对象
(1)使用 set() 方法,保存 Connection 对象
(2)使用 get() 方法,获取 Connection 对象
2、前提:所有操作都必须在同一个线程中完成
3、使用 Filter 统一给所有 Service 方法,加上 try-catch
4、所有 Service 方法产生的异常,必须抛出到 Filter
5、将所有异常都统一交给 Tomcat,让 Tomcat 展示错误信息页面
(1)在 web.xml 中可以通过错误页面配置来进行管理
<!-- error-page 标签,配置(服务器出错后)自动跳转的页面 -->
<error-page>
<error-code><!-- error-code 表示错误类型 --></error-code>
<location><!-- location 表示要跳转去的页面路径 --></location>
</error-page>
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】凌霞软件回馈社区,博客园 & 1Panel & Halo 联合会员上线
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】博客园社区专享云产品让利特惠,阿里云新客6.5折上折
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 微软正式发布.NET 10 Preview 1:开启下一代开发框架新篇章
· 没有源码,如何修改代码逻辑?
· PowerShell开发游戏 · 打蜜蜂
· 在鹅厂做java开发是什么体验
· WPF到Web的无缝过渡:英雄联盟客户端的OpenSilver迁移实战