java - 使用 JdbcCursorItemReader 进行动态 SQL 查询

标签 java spring spring-batch

我正在使用 java 配置(spring-boot)进行 spring 批处理。我有一个员工 ID 列表,对于每个 ID,我需要运行一个查询(如下所示),然后处理数据。

select * from history where employee_id = ?

据我了解,我们可以使用reader.setPreparedStatementSetter来动态设置上述SQL中的参数。但是,我不确定如何为列表中的每个员工 ID 重复批处理过程。即使我将 reader() 标记为 @StepScope,reader 也只会被调用一次。 (即),该批处理仅运行一次。如有任何帮助,我们将不胜感激。

    List employeeIds = new ArrayList();
    employeeIds.add(1);
    employeeIds.add(2);

    @Bean
    @StepScope
    public ItemReader<History> reader() {
        JdbcCursorItemReader<History> databaseReader = new JdbcCursorItemReader<>();
        databaseReader.setSql("select * from history where employee_id = ?");
        databaseReader.setPreparedStatementSetter(..);
        ....

        return databaseReader;
    }


    @Bean
    public Step step(StepBuilder stepBuilder){
        return stepBuilderFactory.get("sample").
                .reader(reader())
                .processor(processor())
                .writer(writer())
                .build();
    }

最佳答案

所以首先,我不建议您这样做。从理论上讲,并且几乎总是在实践中,打开单个游标比每次单独查询要高效得多。

“更好”的方法是将 ID 列表插入暂存/驱动表中(通常在前面的步骤中,每当您从原始源获取 ID 列表时),然后将查询更改为如下所示:

select * from history where employee_id in (select id from driving_table)
<小时/>

或者,您至少可以将查询更改为:

select * from history where employee_id in ( ? ) 

并向其传递 ID 列表(此处要小心,因为某些数据库限制查询中的参数数量)。如果您的列表有可能超出该限制,您需要打开一个新游标,对列表进行有效分页。

关于java - 使用 JdbcCursorItemReader 进行动态 SQL 查询,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42909930/

相关文章:

java - 使用异步 Servlet 进行 Web 推送通知

java - 想要使用共享的 @BeforeClass/@AfterClass 和 Spring App Context 运行许多 jUnit 测试类

java - 是否可以在运行时创建 Java 模型对象并动态映射 Spring Batch Reader 中的字段?

java - MongoItemReader 中的限制和跳过选项

java - 应用程序之间如何交换信号?

java - 文件可用后立即运行 Spring Batch 作业

java - 'MaxRAM' JVM 参数表示什么?

java - 如何防止我的 JPanel 重新调整

java - 如何在 Mac os x 中将 Java 应用程序与本地数据库连接

Spring 启动 : Executing the Newer version of SQL file each time we rebuild the application