Spring batch 单事务中的Spring批处理tasklet
我使用FlatFileItemReader创建了一个spring批处理作业,它从一个分隔文件中读取数据,然后使用JdbcBatchItemWriter写入DB。我的setp配置如下所示Spring batch 单事务中的Spring批处理tasklet,spring-batch,Spring Batch,我使用FlatFileItemReader创建了一个spring批处理作业,它从一个分隔文件中读取数据,然后使用JdbcBatchItemWriter写入DB。我的setp配置如下所示 <batch:step id="step1"> <batch:tasklet> <batch:chunk reader="fileReader" writer="dbWriter" commit-interva
<batch:step id="step1">
<batch:tasklet>
<batch:chunk reader="fileReader"
writer="dbWriter" commit-interval="100">
</batch:chunk>
</batch:tasklet>
</batch:step>
上面的配置是为每100行打开单独的事务,因此如果在完成tasklet(步骤1)之前发生故障,则我无法恢复以前提交的行。是否有办法在单个事务中运行整个tasklet
注意:我正在使用MapJobRepositoryFactoryBean作为作业存储库,不想在数据库中创建元表以重新启动。在Spring batch中,一个作业一次只能有一个事务 请注意下图,我们可以看到事务在步骤开始时打开,并在步骤结束时提交 事实上,使用SpringBatch的一个主要优点是,作为开发人员,我们不必担心事务管理。即使出现故障,它也会自动回滚整个未提交的事务 (我上次使用Spring Batch已经有一段时间了,我希望我的理解仍然有效:p)不使用面向chuck的tasklet,只需创建一个简单的tasklet即可。默认情况下,简单的tasklet将在单个事务中运行。考虑到您已经构建了reader和writer,您可以编写一个tasklet,它模仿面向chuck的步骤所做的工作(只是向您展示想法的伪代码):
公共类ReaderWriterTasklet实现Tasklet{
私人项目阅读器;
私人项目作者;
//和相应的二传手
公共重复状态执行(STEP供款,
ChunkContext(上下文){
列表区块=新建LinkedList();
while(true){
T item=reader.read();
如果(项==null){
打破
}否则{
添加(项);
}
}
writer.write(块);
返回RepeatStatus.FINISHED;
}
}
(我相信您应该已经知道如何定义运行tasklet的步骤了,对吧?那么我将跳过该步骤)
另一个肮脏的方法是继续使用区块,并将提交间隔设置为
Integer.MAX\u VALUE
。通过这样做,面向块的步骤将不断从读取器获取项,直到它到达末尾,并在一个大块中写入写入器,这一切都发生在一个事务中。当我们在project和@EnableBatchProcessing中使用spring批处理时,注释将为其默认表创建自己的事务。因此,如果您想在我们的应用程序表中执行任何插入、更新或删除操作。我们必须提到JpaTransactionManager,而不是默认的spring批处理事务。
public class ReaderWriterTasklet<T> implements Tasklet {
private ItemReader<T> reader;
private ItemWriter<T> writer;
// and corresponding setters
public RepeatStatus execute(StepContribution contribution,
ChunkContext chunkContext) {
List<T> chunk = new LinkedList<T>();
while (true) {
T item = reader.read();
if (item == null) {
break;
} else {
chunk.add(item);
}
}
writer.write(chunk);
return RepeatStatus.FINISHED;
}
}