在面向读写块的流程中,Spring Batch在哪里提交?

时间:2018-08-02 08:07:44

标签: java spring-batch commit spring-jdbc spring-transactions

在我的Java项目中,我正在使用Spring Boot进行面向块的读取(FlatFileItemReader)-写入(JdbcBatchItemWriter)过程。使用HikariCp数据源。

查看Spring批处理jdbc writer,我们可以找到该部分:

               //some code
                @Override
                public int[] doInPreparedStatement(PreparedStatement ps) throws SQLException, DataAccessException {
                    for (T item : items) {
                        itemPreparedStatementSetter.setValues(item, ps);
                        ps.addBatch();
                    }
                    return ps.executeBatch();
                }
              //some code

因此基本上,如果我的Hikari数据源的setAutocommit参数设置为 true ,则意味着ps.executeBatch()之后,我的数据库将被更新。

第一个问题,在PreparedStatement.executeBatch()它如何精确处理?它提交每个sql语句还是在每个sql语句的结尾?

setAutocommit参数为 false 的情况下,ps.executeBatch()之后不应更新该参数。

由于Spring批处理应管理事务,因此应进行提交。我试图找到它在哪里作出承诺,以更好地理解我遇到的问题。展望ChunkOrientedTaskletSimpleChunkProcessorTransactionTemplate,我找不到它在哪里进行提交。

所以我的第二个问题是, Spring批处理在面向块的进程中的确切位置是哪里?

编辑:使用Spring批处理3.0.7

编辑:似乎已在AbstractPlatformTransactionManager.processCommit(DefaultTransactionStatus status)中进行了处理,但仍然无法理解。

2 个答案:

答案 0 :(得分:1)

您的自动提交参数无关紧要,Spring会进行管理并在其认为合适(并且确实合适)时覆盖它。

您可以set the commit interval定义要提交的频率。

是否应该更改它完全取决于您打算如何批处理,执行是否失败,是否应该跳过或重试这些情况以及其他类似的事情。

答案 1 :(得分:0)

根据Spring Batch docs,关于“何时提交?”的问题,

  

5.1面向块的处理

     

Spring Batch在其大多数情况下使用“面向块的”处理样式   常见的实现。面向块的处理是指阅读   一次记录一个数据,并创建将要写出的“块”,   在交易范围内。从ItemReader读入一项,   交给ItemProcessor并进行汇总。一次项目数   读取等于提交间隔,通过   ItemWriter,然后提交事务。

enter image description here

  

以下是上面显示的相同概念的代码表示:

List items = new Arraylist();
for(int i = 0; i < commitInterval; i++){
    Object item = itemReader.read()
    Object processedItem = itemProcessor.process(item);
    items.add(processedItem);
}
itemWriter.write(items);

因此,如果您要使用Spring Batch,则不要搞砸设置auto-commit,因为您应该信任框架为您处理的事情。下面的部分显示了如何配置的示例:

  

5.1.1配置步骤

     

尽管步骤所需的依赖项列表相对较短,   这是一个非常复杂的类,可能包含许多   合作者。为了简化配置,Spring Batch   可以使用命名空间:

<job id="sampleJob" job-repository="jobRepository">
    <step id="step1">
        <tasklet transaction-manager="transactionManager">
            <chunk reader="itemReader" writer="itemWriter" commit-interval="10"/>
        </tasklet>
    </step>
</job>
     

上面的配置代表了唯一需要的依赖项   创建一个面向项目的步骤:

     
      
  • reader-提供处理项目的ItemReader。

  •   
  • writer-处理ItemReader提供的项目的ItemWriter。

  •   
  • transaction-manager-Spring的PlatformTransactionManager,将用于在处理期间开始和提交事务。

  •   
  • job-repository-JobRepository,将在以下过程中定期存储StepExecution和ExecutionContext   处理(在提交之前)。对于串联(一个   在)中定义,它是元素上的属性;   对于独立步骤,它被定义为   

  •   
  • commit-interval-提交事务之前将要处理的项目数。

  •