0

我正在维护一个使用 Spring Batch 编写的遗留应用程序,需要对其进行调整以永远不会丢失数据。我必须从各种 web 服务中读取(每个步骤一个),然后写入远程数据库。当与 DB 的连接断开时,事情会变得很糟糕,因为从 web 服务读取的所有项目都被丢弃(不能两次读取相同的项目),并且由于无法写入而导致数据丢失。

我需要设置 Spring Batch 以将已读取的数据保留在一个步骤上,以便在下次运行该步骤时重试写入操作。在写操作成功结束之前,相同的步骤不能读取更多的数据。当无法写入时,该步骤应保留读取的数据并将执行传递到下一步,一段时间后,当失败的步骤再次运行时,它不应读取另一项,而是重试失败的写入操作.

批处理应用程序应该在无限循环中运行,并且每个步骤都应该从一个不同的来源收集数据。应该暂时跳过失败的写入操作(保留读取数据),以免延迟其他步骤,但应该在下次调用它们时从写入操作恢复。

除了官方文档,我还在研究各种网络资源,但 Spring Batch 并不是我遇到的最直观的文档。

这可以实现吗?如果是,如何?

4

2 回答 2

0

我不知道这是否适合您,但这是我对您的配置的看法。

由于您有两个可能发生故障的远程源,让我们用两个作业(而不是两个步骤)对整个系统进行分区

工作甲

第 1 步:Tasklet 检查共享文件夹中的文件。如果文件存在,请不要继续下一步。写JOB B的时候会更容易理解

第 2 步:Web 服务到文件 从您的 Web 服务读取并将结果写入共享文件夹中的平面文件。由于您将使用平面文件进行输出,因此您将解决“从 Web 服务读取的所有项目都被丢弃并且数据因无法写入而丢失”的问题。

使用 Quartz 或同等工具来安排此作业。

JOB B 轮询共享文件夹以获取生成的文件并使用该文件创建一个作业启动器(file.getWhere 作为作业参数)。Spring 集成项目可能有助于此轮询。

第1步:从文件中读取,将它们写入远程数据库,如果写入数据库成功,则移动/删除文件。

由于作业启动源自文件中的轮询,因此不需要调度。

样品执行

时间 0:共享文件夹中没有文件

时间 1:从 Web 服务读取并写入共享文件夹

时间 2:作业 B 文件轮询发生,尝试写入 db。

如果成功,系统继续执行。

如果不是,当作业 A 尝试在其预定时间执行时,它将跳过从 Web 服务读取,因为文件仍然存在于共享文件夹中。它将跳过,直到作业 B 使用文件。

我不想详细介绍实现细节,但 Spring Batch 可以处理所有这些情况。希望这会有所帮助。

于 2012-12-18T16:58:18.627 回答
0

如果作业失败,您可以将需要保留的数据写入批处理步骤的 ExecutionContext。您可以使用以下数据再次重新启动作业:

步骤执行由 StepExecution 类的对象表示。每个执行都包含对其相应步骤和 JobExecution 的引用,以及与事务相关的数据,例如提交和回滚计数以及开始和结束时间。此外,每个步骤执行都将包含一个 ExecutionContext,其中包含开发人员需要在批处理运行中持久保存的任何数据,例如重新启动所需的统计信息或状态信息

更多来自:http ://static.springsource.org/spring-batch/reference/html/domain.html#domainStepExecution

于 2012-12-18T16:40:28.903 回答