【发布时间】:2019-11-20 06:21:24
【问题描述】:
给定一个 Spring Batch 使用分区的作业:
<job id="reportingJob" xmlns="http://www.springframework.org/schema/batch">
<batch:listeners>
<batch:listener ref="reportingJobExecutionListenerr" />
</batch:listeners>
<batch:step id="reportingMasterStep">
<partition step="reportingSlaveStep"
partitioner="reportingPartitioner">
<batch:handler grid-size="10" task-executor="taskExecutor" />
</partition>
</batch:step>
</job>
而reportingSlaveStep 定义为:
<step id="reportingSlaveStep" xmlns="http://www.springframework.org/schema/batch">
<job ref="reportingSlaveJob" />
</step>
而reportingSlaveJob 定义为:
<job id="reportingSlaveJob" xmlns="http://www.springframework.org/schema/batch">
<batch:listeners>
<batch:listener ref="reportsOutputListener" />
</batch:listeners>
<batch:split id="reportsCreationSplit"
task-executor="taskExecutor">
<batch:flow>
<batch:step id="basicReportStep">
<tasklet throttle-limit="5" task-executor="taskExecutor">
<batch:chunk reader="basicReportReader"
writer="basicReportWriter" commit-interval="500" />
</tasklet>
</batch:step>
</batch:flow>
<batch:flow>
<batch:step id="advancedReportStep">
<tasklet throttle-limit="5" task-executor="taskExecutor">
<batch:chunk reader="advancedReportDataReader" writer="advancedReportWriter"
commit-interval="500" />
</tasklet>
</batch:step>
</batch:flow>
</batch:split>
</job>
我现在有 2 个问题:
- 我想为每个分区创建一个新的
reportsOutputListener实例。我可以通过将reportsOutputListener设为Step范围 bean 来实现这一点吗? - 我希望能够访问为
reportingJob创建的相同jobExecutionContext,以便在reportingSlaveJob中访问。我是否需要对此进行任何特殊处理,或者reportingJob中的jobExecutionContext实例是否也被reportingSlaveStepSlaveJob使用? -
编辑:当我运行上述作业时,有时我会收到一个异常,说“该作业的作业执行已经在运行”,而其他时候我在
MapExecutionContextDao.java:130上得到一个NullPointerException。
EDIT :另请注意,对于第 2 点,slaveJob 无法访问 @987654340 在 stepExecutionContext 中添加的值(在 spring config xml 中使用 #{stepExecutionContext['msbfBatchId']} 访问) @。 stepExecutionContext 中针对密钥的值显示为 null。
【问题讨论】:
-
对于问题 1,答案是肯定的。对于问题 2,我需要有一个可以使用的示例,但我的想法如下:由于子作业(reportingSlaveJob)只不过是一个步骤(JobStep 类型),因此应该可以以某种方式访问一旦子作业的步骤执行在范围内(在这种情况下
stepExecution.getJobExecution().getExecutionContext()将给出您正在寻找的执行上下文),主作业(reportingJob)的父执行上下文。 -
@MahmoudBenHassine 看来我必须做一些特殊处理才能将值从
reportingJob级联到reportingSlaveJob。我不得不编写一个自定义的JobParametersExtractor,因为Spring Batch 3.0 中的DefaultJobParametersExtractor出于某种原因没有将作业执行上下文数据复制到reportingSlaveJob的jobParameters。 -
@MahmoudBenHassine 感谢您的回复。请看我的编辑。对于 2) 所有由 reportingPartitioner 添加到 stepExecutionContext 的值都显示为 null。 (在 spring xml 配置中使用 #{stepExecutionContext['myKey']} 访问)。还添加了第 3 点,表明这种设置似乎不起作用。我正在使用 Spring Batch 3.0。我现在只有一个悬而未决的问题需要解决。
jobExecution.getExecutionContext在reportsOutputListener中返回null,这是一个步骤范围的作业执行侦听器。
标签: java spring-batch listener partitioning