了解在Web容器中启动Spring批处理作业

时间:2011-10-04 07:20:07

标签: java spring spring-batch web-container

当我发现我们必须使用 TaskExecutor 接口(异步版本)的不同实现时,我正在阅读Spring Batch文档,如果我们有效地运行批处理作业的话来自Web容器。

我假设Http请求会触发批处理作业。据我所知,当客户端通过 JobLauncher 接口的run方法启动作业时,客户端必须等待 JobExecution 对象返回并返回典型的批处理作业最后会运行几个小时,如果同步执行作业,这可能不太可行。现在, AsyncTaskExecutor 将在单独的线程中执行每个步骤,并立即以UNKNOWN状态返回 JobExecution 对象。

首先,有人可以向我解释一下,如何从客户端 - 服务器连接的角度来看?在每种情况下,客户端是否会在终止会话之前等待批处理完成?或者,客户端不知道批处理作业的退出状态?整个问题与连接必须保持到批处理结束?

例如,假设客户端有一个发送HTTP get请求的网页,该请求由servlet的 doget 方法提供。此方法调用作业启动程序的 run 方法。此方法将返回 JobExecution 对象。其余的故事如上所述。

谢谢, 阿迪亚。

2 个答案:

答案 0 :(得分:4)

它取决于你的servlet在调用run方法并收到JobExecution对象之后所做的事情。我将假设 doget 方法只是在调用run之后返回。

如果使用异步执行程序,则将同步执行对作业启动程序上的run方法的调用。也就是说,调用将等到批处理作业完成并返回JobExecution对象。从连接的角度来看,客户端的HTTP连接将在整个批处理作业期间保持打开状态。当servlet的doGet方法返回时(或者在某些级别遇到某种超时,例如防火墙或套接字读取超时)之前,HTTP连接将被关闭。

如果使用异步执行程序,则会立即返回对run方法的调用。之后,doGet方法将返回,HTTP响应将被发送到客户端,连接将被关闭(假设没有HTTP保持活动状态)。

答案 1 :(得分:0)

从Web容器中运行作业

通常,作业是从命令行启动的。但是,在很多情况下,从JobLauncher启动是更好的选择。许多此类用例包括报告,临时作业运行和Web应用程序支持。因为按定义批处理作业长时间运行,所以最重要的问题是确保异步启动作业:

enter image description here

这里,Spring MVC控制器使用已配置为异步启动的JobExecution启动作业,该作业立即返回HttpRequest。作业可能仍在运行,但是,这种非阻塞行为允许控制器立即返回,这在处理@Controller public class JobLauncherController { @Autowired JobLauncher jobLauncher; @Autowired Job job; @RequestMapping("/jobLauncher.html") public void handle() throws Exception{ jobLauncher.run(job, new JobParameters()); } } 时是必需的。

以下是一个例子:

def update_mini_batch(self, mini_batch, eta, lmbda, n):
    """Update the network's weights and biases by applying gradient
    descent using backpropagation to a single mini batch.  The
    ``mini_batch`` is a list of tuples ``(x, y)``, ``eta`` is the
    learning rate, ``lmbda`` is the regularization parameter, and
    ``n`` is the total size of the training data set.

    """
    nabla_b = [np.zeros(b.shape) for b in self.biases]
    nabla_w = [np.zeros(w.shape) for w in self.weights]
    for x, y in mini_batch:
        delta_nabla_b, delta_nabla_w = self.backprop(x, y)
        nabla_b = [nb+dnb for nb, dnb in zip(nabla_b, delta_nabla_b)]
        nabla_w = [nw+dnw for nw, dnw in zip(nabla_w, delta_nabla_w)]
    self.weights = [(1-eta*(lmbda/n))*w-(eta/len(mini_batch))*nw
                    for w, nw in zip(self.weights, nabla_w)]
    self.biases = [b-(eta/len(mini_batch))*nb
                   for b, nb in zip(self.biases, nabla_b)]

source