编辑
2023-11-11
Tomcat源码学习
00
请注意,本文编写于 546 天前,最后修改于 546 天前,其中某些信息可能已经过时。

Tomcat中的Listener机制允许我们在Servlet Context生命周期中的特定时间点执行自定义代码。

Tomcat支持以下几种类型的Listener:

  1. ServletContextListener

装配在ServletContext级别。在web应用启动和关闭时触发。

  1. ServletRequestListener

装配在ServletRequest级别。在请求开始和结束时触发。

  1. HttpSessionListener

装配在HttpSession级别。在Session开始、结束和失效时触发。

  1. ServletRequestAttributeListener

监听请求属性(Attribute)的修改事件。

  1. HttpSessionAttributeListener

监听Session属性的修改事件。

Listener需要实现相应的接口,例如ServletContextListener需实现ServletContextListener接口。

在web.xml中配置标签来注册Listener。

Listener的执行顺序:

  1. ServletContextListener - 上下文启动

  2. ServletRequestListener - 请求开始

  3. Servlet - 服务

  4. ServletRequestListener - 请求结束

  5. HttpSessionListener - Session开始

  6. HttpSessionListener - Session结束

  7. ServletContextListener - 上下文关闭

Listener提供了监听Servlet Context生命周期不同阶段的回调接口,我们可以在这些时机进行自定义操作,如资源初始化、统计收集等。它可以很好地进行应用编程。

java
private class Listener implements AsyncListener { @Override public void onComplete(AsyncEvent event) throws IOException { if (endTiming == EndTiming.INLINE) { endLatch.countDown(); } } @Override public void onTimeout(AsyncEvent event) throws IOException { // Need to handle timeouts for THREAD_COMPLETES_AFTER_SERVLET_EXIT in the listener to // avoid concurrency issues. if (endTiming == EndTiming.THREAD_COMPLETES_AFTER_SERVLET_EXIT) { switch (asyncEnd) { case COMPLETE: { asyncContext.complete(); break; } case DISPATCH: { dispatch = true; asyncContext.dispatch(); break; } default: // NO-OP } } if (servletRequest.isAsyncStarted() == asyncEnd.isNone()) { failed.set(false); } endLatch.countDown(); } @Override public void onError(AsyncEvent event) throws IOException { // Need to handle errors for THREAD_COMPLETES_AFTER_SERVLET_EXIT in the listener to // avoid concurrency issues. if (endTiming == EndTiming.THREAD_COMPLETES_AFTER_SERVLET_EXIT) { switch (asyncEnd) { case ERROR_COMPLETE: { asyncContext.complete(); break; } case ERROR_DISPATCH: { dispatch = true; asyncContext.dispatch(); break; } default: // NO-OP } if (servletRequest.isAsyncStarted() == asyncEnd.isNone()) { failed.set(false); } endLatch.countDown(); } } @Override public void onStartAsync(AsyncEvent event) throws IOException { // NO-OP } }

本文作者:yowayimono

本文链接:

版权声明:本博客所有文章除特别声明外,均采用 BY-NC-SA 许可协议。转载请注明出处!