Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/svg/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 如何在HttpServlet中处理大数据?_Java_Servlets_Jakarta Ee - Fatal编程技术网

Java 如何在HttpServlet中处理大数据?

Java 如何在HttpServlet中处理大数据?,java,servlets,jakarta-ee,Java,Servlets,Jakarta Ee,在我的JavaEE应用程序中,有一个servlet来处理大型数据流程。这个过程为数据库中的所有实体(1300万条记录)编制索引,至少需要15分钟才能完成。由于服务器处理时间过长,客户端引发超时异常 @WebServlet("/index") public class IndexServlet extends HttpServlet { private static final long serialVersionUID = 1L; private Logger logger =

在我的JavaEE应用程序中,有一个servlet来处理大型数据流程。这个过程为数据库中的所有实体(1300万条记录)编制索引,至少需要15分钟才能完成。由于服务器处理时间过长,客户端引发超时异常

@WebServlet("/index")
public class IndexServlet extends HttpServlet {

    private static final long serialVersionUID = 1L;
    private Logger logger = Logger.getLogger(this.getClass());

    @EJB
    private AddressSession addressSession;

    protected void service(HttpServletRequest request,
            HttpServletResponse response) {

        try {
            addressSession.index();
        } catch (InterruptedException e) {
            logger.error(e);
        }
    }
}

我的问题是如何处理这种情况?我应该使用异步处理吗?

对于需要很长时间的流程,web界面应该只是一个“作业提交”,它会立即确认收到请求并将作业排队等待处理。然后将这个“自然”的后端过程与web层分离

例如,您不使用http线程池来进行后端处理。为处理提交的作业单独设置一个。您可以创建执行器,例如使用

ExecutorService executorService = Executors.newFixedThreadPool(10);
然后,当收到请求时,您可以按如下方式提交作业:

executorService.execute(new Runnable() {
    public void run() {
        // processing
    }
});
现在,如果您还想通过一些web界面提供有关工作状态的信息,您需要做更多的工作。您可能希望为提交的作业分配一个唯一的id,并将其与回执一起返回


在这种情况下,因为您使用的是EJB(如果您使用的是EJB3.1或更高版本),所以不需要自己编写执行器。您可以使用EJB方法上的注释以声明方式执行此异步处理。

对于耗时如此长的进程,web界面应该只是一个“作业提交”,它立即确认收到请求并将作业排队等待处理。然后将这个“自然”的后端过程与web层分离

例如,您不使用http线程池来进行后端处理。为处理提交的作业单独设置一个。您可以创建执行器,例如使用

ExecutorService executorService = Executors.newFixedThreadPool(10);
然后,当收到请求时,您可以按如下方式提交作业:

executorService.execute(new Runnable() {
    public void run() {
        // processing
    }
});
现在,如果您还想通过一些web界面提供有关工作状态的信息,您需要做更多的工作。您可能希望为提交的作业分配一个唯一的id,并将其与回执一起返回

在这种情况下,因为您使用的是EJB(如果您使用的是EJB3.1或更高版本),所以不需要自己编写执行器。您可以使用EJB方法上的注释以声明方式执行此异步处理。

启用异步支持 正如@user2494817所说,在这种情况下可以使用异步处理。要在servlet上启用异步处理,请在
@WebServlet
注释中将参数
asynchsupported
设置为true:

@WebServlet(urlPatterns = {"/index"}, asyncSupported = true)
使用异步上下文 然后我们需要使用
javax.servlet.AsyncContext
类,它提供了在服务方法内部执行异步处理所需的功能。要获取AsyncContext的实例,请对服务方法的请求对象调用
startAsync()
方法

AsyncContext asyncContext = request.startAsync();
此调用将请求置于异步模式,并确保 退出服务方法后未提交响应。您必须在阻塞操作完成后在异步上下文中生成响应,或者将请求分派到另一个servlet

这在中进行了描述。我的解决方案只考虑一个用户,对于其他用例,我们可能需要更复杂的机制


启用异步支持 正如@user2494817所说,在这种情况下可以使用异步处理。要在servlet上启用异步处理,请在
@WebServlet
注释中将参数
asynchsupported
设置为true:

@WebServlet(urlPatterns = {"/index"}, asyncSupported = true)
使用异步上下文 然后我们需要使用
javax.servlet.AsyncContext
类,它提供了在服务方法内部执行异步处理所需的功能。要获取AsyncContext的实例,请对服务方法的请求对象调用
startAsync()
方法

AsyncContext asyncContext = request.startAsync();
此调用将请求置于异步模式,并确保 退出服务方法后未提交响应。您必须在阻塞操作完成后在异步上下文中生成响应,或者将请求分派到另一个servlet

这在中进行了描述。我的解决方案只考虑一个用户,对于其他用例,我们可能需要更复杂的机制



您回答了自己的问题async。另外,如果您的客户端可以等待15分钟,您可以增加EJB的事务超时时间。您回答了自己的问题async。此外,如果您的客户端可以等待15分钟,您可以增加EJB的事务超时时间。您的回答听起来很有趣,我来测试。谢谢你,纳扎勒克!谢谢顺便说一下,我认为servlet上的“异步支持”与您的用例无关,因为它们主要用于将servlet实现更改为非阻塞实现。客户端仍在等待,直到整个处理完成。这不是你想要的。你的答案解释得很好,非常感谢。我在会话bean方法
AddressSession#index()
中标记了
@Asynchronous
,效果很好。你的答案听起来很有趣,我会测试它。谢谢你,纳扎勒克!谢谢顺便说一下,我认为servlet上的“异步支持”与您的用例无关,因为它们主要用于将servlet实现更改为非阻塞实现。客户端仍在等待,直到整个处理完成。这不是你想要的。你的答案解释得很好,非常感谢。我在会话bean方法
AddressSession#index()
中标记了
@Asynchronous
,效果很好。