如何进行Spring Batch步骤取决于前一步骤?

时间:2017-08-29 08:59:42

标签: java spring-batch jobs tasklet

我正在使用Spring Batch从CSV文件中读取一些数据并将其放入数据库中。 我的批处理作业必须包含两个步骤:

  1. 检查文件(名称,扩展名,内容..)
  2. 从CSV读取行并将其保存在DB(ItemReader,ItemProcessor, ItemWriter ..)
  3. 如果Step 2生成错误(文件不符合,文件不存在......),则不得执行{p> Step 1

    仅供参考,我使用没有XML配置的Spring Batch!只有注释: 这是我的作业配置类的样子:

    @Configuration
    @EnableBatchProcessing
    public class ProductionOutConfig {
    
        @Autowired
        private StepBuilderFactory steps;
    
        @Autowired
        private JobBuilderFactory jobBuilderFactory;
    
    
        @Autowired
        private ProductionOutTasklet productionOutTasklet;
    
        @Autowired
        private CheckFilesForProdTasklet checkFilesForProdTasklet;
    
        @Bean
        public Job productionOutJob(@Qualifier("productionOut")Step productionOutStep,
                                    @Qualifier("checkFilesForProd") Step checkFilesForProd){
            return jobBuilderFactory.get("productionOutJob").start(checkFilesForProd).next(productionOutStep).build();
        }
    
        @Bean(name="productionOut")
        public Step productionOutStep(){
            return steps.get("productionOut").
                    tasklet(productionOutTasklet)
                    .build();}
    
        @Bean(name = "checkFilesForProd")
        public Step checkFilesForProd(){
            return steps.get("checkFilesForProd")
                    .tasklet(checkFilesForProdTasklet)
                    .build();
        }
    }
    

2 个答案:

答案 0 :(得分:3)

您正在寻找的是Spring Batch的默认行为,即如果上一步失败,则不会执行下一步。要将当前步骤标记为失败步骤,您需要抛出未捕获的运行时异常。

如果未处理异常,则弹出批次将该步骤标记为失败,并且不会执行下一步骤。所以你需要做的就是在失败的场景中抛出异常。

对于复杂的工作流程,您可能希望使用 - JobExecutionDeciderProgrammatic Flow Decisions

答案 1 :(得分:1)

正如文档所指定的那样,如果前一状态的退出状态与给定模式匹配,则可以使用“on”方法开始转换到新状态。

您的代码可能类似于以下内容:

    return jobBuilderFactory.get("productionOutJob")
           .start(checkFilesForProd)
           .on(ExitStatus.FAILED.getExitCode()).end()
           .from(checkFilesForProd)
           .on("*")
           .to(productionOutStep)
           .build();