Parameters 在Spring批处理中使用StepScope注释时的WriterNotOpenException
我有一个习惯性的作家,他写得很好;但是,我希望通过JobParameters设置输出文件的名称,而不是在配置中使用固定字符串。 为了做到这一点,我添加了@StepScope注释和参数,就像我对ItemReader所做的那样 项目编写器声明Parameters 在Spring批处理中使用StepScope注释时的WriterNotOpenException,parameters,spring-batch,writer,Parameters,Spring Batch,Writer,我有一个习惯性的作家,他写得很好;但是,我希望通过JobParameters设置输出文件的名称,而不是在配置中使用固定字符串。 为了做到这一点,我添加了@StepScope注释和参数,就像我对ItemReader所做的那样 项目编写器声明 @Bean @StepScope public ItemWriter<CityProcessed> writer(@Value("#{jobParameters[inputFile]}") String inputFile, @Value("#{j
@Bean
@StepScope
public ItemWriter<CityProcessed> writer(@Value("#{jobParameters[inputFile]}") String inputFile, @Value("#{jobParameters[outputFile]}") String outputFile) {
// String inputFile = "D:/cities.csv";
// String outputFile = "D:/compterendu.csv";
FlatFileItemWriter<CityCRE> writer = new FlatFileItemWriter<CityCRE>();
FileSystemResource isr;
isr = new FileSystemResource(new File(outputFile));
writer.setResource(isr);
DelimitedLineAggregator<CityCRE> aggregator = new DelimitedLineAggregator<CityCRE>();
aggregator.setDelimiter(";");
BeanWrapperFieldExtractor<CityCRE> beanWrapper = new BeanWrapperFieldExtractor<CityCRE>();
beanWrapper.setNames(new String[]{
"nom", "pays", "identifiantBase", "c/m"
});
aggregator.setFieldExtractor(beanWrapper);
writer.setLineAggregator(aggregator);
CityItemWriter itemWriter = new CityItemWriter();
writer.setFooterCallback(itemWriter);
writer.setHeaderCallback(itemWriter);
itemWriter.setDelegate(writer);
itemWriter.setInputFileName(inputFile);
return itemWriter;
}
@Bean
public Step stepImport(StepBuilderFactory stepBuilderFactory, ItemReader<CityFile> reader, ItemWriter<CityProcessed> writer, ItemProcessor<CityFile, CityProcessed> processor) {
return stepBuilderFactory
.get("step1")
.<CityFile, CityProcessed> chunk(10)
.reader(reader(null))
.processor(processor)
.writer(writer(null, null))
.build();
}
@Bean
@步进镜
公共ItemWriter编写器(@Value(“{jobParameters[inputFile]}”)字符串输入文件,@Value(“{jobParameters[outputFile]}”)字符串输出文件){
//字符串inputFile=“D:/cities.csv”;
//字符串outputFile=“D:/compterendu.csv”;
FlatFileItemWriter writer=新的FlatFileItemWriter();
文件系统资源isr;
isr=新文件系统资源(新文件(outputFile));
编写器设置资源(isr);
DelimitedLineAggregator aggregator=新的DelimitedLineAggregator();
aggregator.setDelimiter(“;”);
BeanWrapperFieldExtractor beanwraper=新的BeanWrapperFieldExtractor();
beanWrapper.setNames(新字符串[]){
“名称”、“付款”、“标识基础”、“付款方式”
});
聚合器。setFieldExtractor(BeanRapper);
writer.setLineAggregator(聚合器);
CityItemWriter itemWriter=新的CityItemWriter();
setFooterCallback(itemWriter);
writer.setHeaderCallback(itemWriter);
itemWriter.setDelegate(编写器);
setInputFileName(inputFile);
返回项目编写器;
}
步骤声明
@Bean
@StepScope
public ItemWriter<CityProcessed> writer(@Value("#{jobParameters[inputFile]}") String inputFile, @Value("#{jobParameters[outputFile]}") String outputFile) {
// String inputFile = "D:/cities.csv";
// String outputFile = "D:/compterendu.csv";
FlatFileItemWriter<CityCRE> writer = new FlatFileItemWriter<CityCRE>();
FileSystemResource isr;
isr = new FileSystemResource(new File(outputFile));
writer.setResource(isr);
DelimitedLineAggregator<CityCRE> aggregator = new DelimitedLineAggregator<CityCRE>();
aggregator.setDelimiter(";");
BeanWrapperFieldExtractor<CityCRE> beanWrapper = new BeanWrapperFieldExtractor<CityCRE>();
beanWrapper.setNames(new String[]{
"nom", "pays", "identifiantBase", "c/m"
});
aggregator.setFieldExtractor(beanWrapper);
writer.setLineAggregator(aggregator);
CityItemWriter itemWriter = new CityItemWriter();
writer.setFooterCallback(itemWriter);
writer.setHeaderCallback(itemWriter);
itemWriter.setDelegate(writer);
itemWriter.setInputFileName(inputFile);
return itemWriter;
}
@Bean
public Step stepImport(StepBuilderFactory stepBuilderFactory, ItemReader<CityFile> reader, ItemWriter<CityProcessed> writer, ItemProcessor<CityFile, CityProcessed> processor) {
return stepBuilderFactory
.get("step1")
.<CityFile, CityProcessed> chunk(10)
.reader(reader(null))
.processor(processor)
.writer(writer(null, null))
.build();
}
@Bean
公共步骤stepImport(StepBuilderFactory StepBuilderFactory、ItemReader阅读器、ItemWriter编写器、ItemProcessor处理器){
返回stepBuilderFactory
.get(“步骤1”)
.chunk(10)
.读卡器(读卡器(空))
.处理器(处理器)
.writer(writer(null,null))
.build();
}
这段代码不起作用,我得到一个WriterNotOpenException,因为我使用FlatFileItemWriter作为委托
当我尝试为ItemReader使用JobParameters时,我遇到了相同的错误,我必须将返回类型更改为“FlatFileItemReader”(而不是ItemReader)。我不能在这里做同样的事情,因为我需要我的自定义ItemWriter,而不是一个简单的FlatFileItemWriter
我不明白为什么我在添加@StepScope时会出现这个错误,而我的读者没有它就没有问题。我做错了什么
其他信息:
- 当我使用inputFile和outputFile字符串时,我的配置工作正常
- 当我添加@StepScope注释时(即使没有将JobParameters添加为我的writer参数),看起来我有一个错误
返回新的**FlatFileItemWriterBuilder**()
.姓名(“LeiturarquivodeLimitadoWriter”)
.资源(arquivoClienteSaida)
.delimited()
.names(新字符串[]{“nome”、“sobrenome”、“idade”、“email”})
.build();
}
}
消息错误
org.springframework.batch.item.WriterNotOpenException:必须先打开Writer,然后才能将其写入
正常
publicFlatFileItemWriter
LeiturarQuivodeLimitadoWriter(@Value(“#{jobParameters['arquivoSaidaClientes']}”)资源arquivoClienteSaida){
//返回项目->项目.forEach(系统输出::println)
返回新的**FlatFileItemWriterBuilder**()
.姓名(“LeiturarquivodeLimitadoWriter”)
.资源(arquivoClienteSaida)
.delimited()
.names(新字符串[]{“nome”、“sobrenome”、“idade”、“email”})
.build();
}
}
在这种情况下,将publicItemWriter更改为FlatFileItemWriter可以解决这个问题。它可以工作(谢谢),但我仍然不明白为什么我只使用固定字符串,而不必将委托注册为流。对此有什么解释吗?我帮不了你,对不起:(我想静态/范围注册的工作原理不同,但是@MMinella可能会给你正确的解释。