【问题标题】:How to upgrade filters to support Servlet 3.0 asynchronous servlet如何升级过滤器以支持 Servlet 3.0 异步 servlet
【发布时间】:2012-06-03 04:22:15
【问题描述】:

我有一个 servlet,用于从许多第三方 REST 数据点获取数据、集成所有数据并以 HTML 格式报告数据。我还有一个过滤器,它具有以下流程 -

  1. 在请求命中过滤器时创建事件记录,并将 eventrecord 对象添加到请求中
  2. 执行 chain.doFilter - 允许 servlet 向事件记录添加更多详细信息
  3. 在返回浏览器的途中,过滤器获取事件记录对象并记录它。

现在,如果我使用 AsyncContext context = request.getAsyncContext(); 使用异步 servlet,它将与相同的 REST 数据点通信,但当数据准备好时,它将写入响应流而不是等待所有 REST 数据点响应,如何我会重新编写我的过滤器吗?它是否会附加到负责从 REST 数据点刷新数据的线程,以便在处理和刷新所有数据后,它将记录事件记录? 是否有任何通用模式可供我研究以了解如何使用 Servlet 3.0 的异步 servlet 处理此类用例? 我正在使用 JDK 6.0、Tomcat 7.0。

【问题讨论】:

    标签: java-ee-6 server-push servlet-3.0


    【解决方案1】:

    只需在 web-xml 中为您的过滤器添加 @WebFilter(urlPatterns = {"/*" }, asyncSupported = true)

    或添加<async-supported>true</async-supported>

    【讨论】:

    • 这就是将过滤器升级为异步的全部内容吗?在问题中,过滤器也将处理响应。无需更改过滤器即可使用AsyncContext?我很困惑。
    • 这对“返回途中”的处理没有帮助(请参阅问题的第三项),恕我直言,这并不能回答问题。
    【解决方案2】:

    由于我不确定自己如何正确支持检测或诊断过滤器(例如Codahales metrics filters),因此我提供了赏金。

    虽然将<async-supported>true</async-supported> 添加到您的过滤器肯定会使它们看起来有效,但它可能无法获得您期望的结果(在指标的情况下,您的所有请求都会显得非常快)。

    立即在过滤器中获取 AsyncContext 以绑定度量数据but various containers apparently have issues with this 似乎是个好主意,我相信像 Spring 这样的框架也有问题(这可能只是我的旧版本 Spring)。那就是大多数框架都希望请求处理的前半部分是同步的(我可能在这方面大错特错)。

    因此,似乎唯一万无一失的方法就是在框架级别集成过滤器。例如 Spring 提供的org.springframework.web.context.request.async.DeferredResultProcessingInterceptor 有点类似于 AsyncContext 事件。

    这有点令人遗憾,因为并非所有请求都可能由 Web 框架处理,但处理请求的第一部分和实际执行之间还是有区别的(即现在您可能要监控两个指标)。

    【讨论】:

      【解决方案3】:

      @WebFilter 注解已在 Java EE 6 中引入。它定义了不同的元素,如 filterName、asyncSupported 和 servletNames 等。@WebFilter 不能在没有 web.xml 的情况下使用,因为@WebFilter 没有定义顺序。 @WebFilter 减少了 web.xml 中的其他配置。

      @WebFilter(filterName="filterOne")
      public class FilterOne implements Filter {
          @Override
          public void init(FilterConfig filterConfig) throws ServletException {
          }
          @Override
          public void doFilter(ServletRequest request, ServletResponse response,
                  FilterChain chain) throws IOException, ServletException {
              System.out.println("Inside filter one.");
              chain.doFilter(request, response);
          }
          @Override
          public void destroy() {
          }
      } 
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2011-05-05
        • 1970-01-01
        • 1970-01-01
        • 2011-06-15
        • 2018-10-01
        • 1970-01-01
        • 2013-03-22
        • 2011-09-29
        相关资源
        最近更新 更多