Spring批处理。如何链接具有不同类型的多个itemProcessor?
Posted
技术标签:
【中文标题】Spring批处理。如何链接具有不同类型的多个itemProcessor?【英文标题】:Spring batch .How to chain multiple itemProcessors with diffrent types? 【发布时间】:2021-01-08 13:36:10 【问题描述】:我必须组成 2 个处理器,如下所示:
processor 1
使用itemProcessor<A,B>
实现itemProcessor
接口(转换数据)。
processor 2
使用itemProcessor<B,B>
实现itemProcessor
接口。(处理转换后的数据)。
CompositeItemProcessor<I, O>
要求委托的类型相同,而且在将其传递给Step
时,该步骤已经配置为固定类型<A,B>
。
我如何将这些处理器与不同类型链接起来并将其分配给step
处理器?
【问题讨论】:
【参考方案1】:您需要使用<A, B>
声明您的步骤以及您的复合处理器。这是一个简单的例子:
import java.util.Arrays;
import org.springframework.batch.core.Job;
import org.springframework.batch.core.JobParameters;
import org.springframework.batch.core.configuration.annotation.EnableBatchProcessing;
import org.springframework.batch.core.configuration.annotation.JobBuilderFactory;
import org.springframework.batch.core.configuration.annotation.StepBuilderFactory;
import org.springframework.batch.core.launch.JobLauncher;
import org.springframework.batch.item.ItemProcessor;
import org.springframework.batch.item.ItemReader;
import org.springframework.batch.item.ItemWriter;
import org.springframework.batch.item.support.CompositeItemProcessor;
import org.springframework.batch.item.support.ListItemReader;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
@Configuration
@EnableBatchProcessing
public class MyJobConfiguration
@Bean
public ItemReader<A> itemReader()
return new ListItemReader<>(Arrays.asList(new A("a1"), new A("a2")));
@Bean
public ItemProcessor<A, B> itemProcessor1()
return item -> new B(item.name);
@Bean
public ItemProcessor<B, B> itemProcessor2()
return item -> item; // TODO process item as needed
@Bean
public ItemProcessor<A, B> compositeItemProcessor()
CompositeItemProcessor<A, B> compositeItemProcessor = new CompositeItemProcessor<>();
compositeItemProcessor.setDelegates(Arrays.asList(itemProcessor1(), itemProcessor2()));
return compositeItemProcessor;
@Bean
public ItemWriter<B> itemWriter()
return items ->
for (B item : items)
System.out.println("item = " + item.name);
;
@Bean
public Job job(JobBuilderFactory jobs, StepBuilderFactory steps)
return jobs.get("job")
.start(steps.get("step")
.<A, B>chunk(2)
.reader(itemReader())
.processor(compositeItemProcessor())
.writer(itemWriter())
.build())
.build();
public static void main(String[] args) throws Exception
ApplicationContext context = new AnnotationConfigApplicationContext(MyJobConfiguration.class);
JobLauncher jobLauncher = context.getBean(JobLauncher.class);
Job job = context.getBean(Job.class);
jobLauncher.run(job, new JobParameters());
class A
String name;
public A(String name) this.name = name;
class B
String name;
public B(String name) this.name = name;
【讨论】:
感谢您的回答,但是它并没有解决问题,我已经看到了compositeItemProcessor 的源代码,它是一个泛型类型,在它期望代表的处理方法中itemProcessors 与 声明的类型相同,这不是我的情况,我有不同类型的 itemProcessors 您询问了如何在组合中使用ItemProcessor<A, B>
和ItemProcessor<B, B>
,这正是示例所显示的。您在哪里看到要求代表具有相同类型的复合材料?代码如下:github.com/spring-projects/spring-batch/blob/…,复合类型为<I, O>
,委托类型为<?, ?>
。
只要复合的类型与步骤所期望的相同,您之间有多少个委托处理器都没有关系:如果步骤读取 A
类型的项目并写入项目D
类型(例如 .<A, D>chunk(5)
),您可以将处理器 A->B
、B->C
和 C->D
作为 CompositeItemProcessor<A, D>
的代表,只要一个处理器的输出类型与链中下一个处理器的输入类型。
感谢 Mahmoud 先生,我在另一部分遇到了问题,抱歉,这已经解决了问题
嗨,我面临着类似的情况,我正在尝试几天来找到解决方案。在以下情况下是否可能或正确的方法是:读取 XML -> ComplexObject -> List以上是关于Spring批处理。如何链接具有不同类型的多个itemProcessor?的主要内容,如果未能解决你的问题,请参考以下文章
您将如何使用 Spring Boot 处理仅具有可选查询参数的 REST API?
Spring Security 具有不同用户详细信息的多个 HTTPSecurity 服务在 Spring Boot 中不起作用
如何在没有 xml 的 Java 配置中使用具有不同数据并具有两个 JdbcBatchItemWritter 的 Spring 批处理 CompositeItemWriter
如何使用基于类的配置设置具有不同基础包、transactionManagerRef 的多个 Spring Data JPA?