2016-08-03 123 views
1

我有一个弹簧批处理作业,它读取,转换并写入Oracle数据库。我通过CommandLineJobRunner实用程序(使用由maven shade插件生成的fat jar +依赖项)运行作业;由于“java堆内存限制已达到”,作业随后中途失败,并且作业未标记为“失败”,而是仍显示“已启动”状态。无法重新启动Spring批处理作业

我试图用同样的工作参数(如文档建议)重新运行工作,但是这给了我这个错误:

5:24:34.147 [main] ERROR o.s.b.c.l.s.CommandLineJobRunner - Job Terminated in error: A job execution for this job is already running: JobInstance: id=1, version=0, Job=[maskTableJob] 

org.springframework.batch.core.repository.JobExecutionAlreadyRunningException:一JobInstance:id = 1,version = 0,Job = [maskTableJob] at org.springframework.batch.core.repository.support.SimpleJobRepository.createJobExecution(SimpleJobRepository.java:120)〜[我已经尝试了各种各样的东西(比如手动的s(s))。将状态设置为FAILED,使用-restart参数)但无济于事。有没有什么我在这里失踪,因为我认为春季批次的一个优点是它能够重新开始他们离开的工作.... !!?

+0

重新运行该作业将无法使用相同的参数。将当前时间添加为重新运行的参数。请参阅http://www.mkyong.com/spring-batch/spring-batch-a-job-instance-already-exists-and-is-complete-for-parameters/。另外结帐的文档:http://docs.spring.io/spring-batch/reference/html/configureJob.html#d5e1320 –

+0

是的,我知道,但我需要重新运行一个特定的工作,因为我希望它继续下去它离开的地方。我的工作处理TB行,可能需要几天的时间才能运行,所以我确实希望每次都从头开始重新开始该死的事情:-) –

+0

我认为步骤中的块处理应该处理这样的事情 –

回答

2

您应该知道的第一件事是Joblauncher不能用于重新启动已经运行的作业。 你得到“JobExecutionAlreadyRunningException”的原因是因为你传递的参数已经存在于数据库中,因此你得到这个异常。

在spring批处理中,如果作业完成时处于“FAILED”状态或“STOPPED”状态,则可以重新启动作业。

JobOperator具有重启方法,可以通过传递以“FAILED”状态或“STOPPED”状态完成的作业执行ID来重启失败的作业。

请注意,如果作业已完成且处于“完成”状态,则无法重新开始作业。 在这种情况下,您将不得不使用新的作业参数提交新作业

如果要手动将作业状态设置为失败,请运行以下查询并使用JobOperator.restart()方法重新启动作业。

update batch_job_execution set status="FAILED", version=version+1 where job_instance_id=jobId; 

对事务管理的不当处理可能是您的工作状态没有更新为“FAILED”状态的一个可能原因。即使作业遇到运行时异常,请确保您的事务正在完成。

+0

非常感谢那个回复。我注意到,如果我的工作完成了status = FAILED和exitstatus = UNKNOWN,那么我可以用相同的工作参数重新运行这个工作,但它似乎不会继续停止,而是开始一个全新的工作。这是使用commandLineJobRunner,所以我会调查使用jobOperator从一个Java主,手动设置退出状态,你说! –

+0

欢迎您,如果您认为我的答案已解决您的问题,请点击勾号将其接受为正确答案:)。 – DevG

+0

我敲了一些Java重新启动作业,通过jobOperator相同的作业参数,它似乎重新启动好。我甚至在日志中看到“恢复工作”,并认为一切都很好,但是看起来我有一个新的执行ID,而且工作步骤从一开始就已经开始。我的目标数据库显示它包含比源证明更多的行,证明它没有继续。 –

相关问题