[Spring 批处理][Mongo] 无法在 ItemReader read() 中读取 jobParameters
[Spring Batch][Mongo] Cannot read jobParameters in ItemReader read()
我已经设置了一个步骤配置和 ItemReader 以从 mongoDB 同一个文件 中读取数据,就像这样...
@Bean("STEP_FETCH_DATA")
public Step fetchDatabaseStep(
ItemReader<ExampleDao> dataReader,
DataProcessor dataProcessor,
DataWriter dataWriter,
@Qualifier("TASK_EXECUTOR") TaskExecutor taskExecutor
) {
log.info("Initialize step: {}", "STEP_FETCH_DATA");
return stepBuilderFactory.get("STEP_FETCH_DATA")
.<ExampleDao, ExampleDao>chunk(chunkSize)
.processor(dataProcessor)
.reader(dataReader)
.writer(dataWriter)
.taskExecutor(taskExecutor)
.build();
}
@Bean("dataReader")
@StepScope
public ItemReader<ExampleDao> read(@Value("#{jobParameters.get(\"batchRunDate\")}") String batchRunDate) throws UnexpectedInputException, ParseException, NonTransientResourceException {
log.info("Reading start... batchRunDate : {}", batchRunDate);
MongoItemReader<ExampleDao> reader = new MongoItemReader<>();
reader.setTemplate(mongoTemplate);
reader.setSort(new HashMap<String, Sort.Direction>() {{
put("_id", Sort.Direction.DESC);
}});
reader.setTargetType(ExampleDao.class);
reader.setQuery("{}");
return reader;
}
从上面的代码,它可以访问我的 jobParameter 并按预期工作。
但是,如果我像这样创建一个 class 来包含我的 mongo ItemReader
@Component
@Slf4j
public class DataReaderExample {
@Autowired
private MongoTemplate mongoTemplate;
@Bean
@StepScope
public ItemReader<ExampleDao> read(@Value("#{jobParameters.get(\"batchRunDate\")}") String
batchRunDate) throws UnexpectedInputException, ParseException, NonTransientResourceException {
log.info("Reading start... batchRunDate : {}", batchRunDate);
MongoItemReader<ExampleDao> reader = new MongoItemReader<>();
reader.setTemplate(mongoTemplate);
reader.setSort(new HashMap<String, Sort.Direction>() {{
put("_id", Sort.Direction.DESC);
}});
reader.setTargetType(ExampleDao.class);
reader.setQuery("{}");
return reader;
}
}
然后像这样设置一个步骤配置。 (注意 .reader(dataReadExample.read(null))。我期望 @Value("#{[= read() 参数中的 40=]("batchRunDate") 将覆盖 null 值)
@Bean("STEP_FETCH_DATA")
public Step fetchDatabaseStep(
DataReaderExample dataReadExample ,
DataProcessor dataProcessor,
DataWriter dataWriter,
@Qualifier("TASK_EXECUTOR") TaskExecutor taskExecutor
) {
log.info("Initialize step: {}", "STEP_FETCH_DATA");
return stepBuilderFactory.get("STEP_FETCH_DATA")
.<ExampleDao, ExampleDao>chunk(chunkSize)
.processor(dataProcessor)
.reader(dataReadExample.read(null))
.writer(dataWriter)
.taskExecutor(taskExecutor)
.build();
}
My log.info("Reading start... batchRunDate : {}", batchRunDate); 批处理将始终打印为空值和@Value ("#{jobParameters.get("batchRunDate") 不工作。好像我无法访问 jobParameters。
谁能向我解释一下这种行为以及如何将 ItemReader 移动到另一个 class。我的目标是将 ItemReader 分离成另一个 class。谢谢!
您的 DataReaderExample
被声明为 @Component
,它应该是 @Configuration
class,您在其中声明了 bean 定义。
我建议将 read
方法更改为 itemReader
或类似的东西,因为它的目的是定义项目 reader bean 而不是实际读取数据。
完成后,您可以在应用程序上下文中导入 DataReaderExample
配置 class 并在您的步骤中自动装配项目 reader:
@Bean("STEP_FETCH_DATA")
public Step fetchDatabaseStep(
ItemReader<ExampleDao> itemReader ,
DataProcessor dataProcessor,
DataWriter dataWriter,
@Qualifier("TASK_EXECUTOR") TaskExecutor taskExecutor
) {
log.info("Initialize step: {}", "STEP_FETCH_DATA");
return stepBuilderFactory.get("STEP_FETCH_DATA")
.<ExampleDao, ExampleDao>chunk(chunkSize)
.processor(dataProcessor)
.reader(itemReader)
.writer(dataWriter)
.taskExecutor(taskExecutor)
.build();
}
我已经设置了一个步骤配置和 ItemReader 以从 mongoDB 同一个文件 中读取数据,就像这样...
@Bean("STEP_FETCH_DATA")
public Step fetchDatabaseStep(
ItemReader<ExampleDao> dataReader,
DataProcessor dataProcessor,
DataWriter dataWriter,
@Qualifier("TASK_EXECUTOR") TaskExecutor taskExecutor
) {
log.info("Initialize step: {}", "STEP_FETCH_DATA");
return stepBuilderFactory.get("STEP_FETCH_DATA")
.<ExampleDao, ExampleDao>chunk(chunkSize)
.processor(dataProcessor)
.reader(dataReader)
.writer(dataWriter)
.taskExecutor(taskExecutor)
.build();
}
@Bean("dataReader")
@StepScope
public ItemReader<ExampleDao> read(@Value("#{jobParameters.get(\"batchRunDate\")}") String batchRunDate) throws UnexpectedInputException, ParseException, NonTransientResourceException {
log.info("Reading start... batchRunDate : {}", batchRunDate);
MongoItemReader<ExampleDao> reader = new MongoItemReader<>();
reader.setTemplate(mongoTemplate);
reader.setSort(new HashMap<String, Sort.Direction>() {{
put("_id", Sort.Direction.DESC);
}});
reader.setTargetType(ExampleDao.class);
reader.setQuery("{}");
return reader;
}
从上面的代码,它可以访问我的 jobParameter 并按预期工作。
但是,如果我像这样创建一个 class 来包含我的 mongo ItemReader
@Component
@Slf4j
public class DataReaderExample {
@Autowired
private MongoTemplate mongoTemplate;
@Bean
@StepScope
public ItemReader<ExampleDao> read(@Value("#{jobParameters.get(\"batchRunDate\")}") String
batchRunDate) throws UnexpectedInputException, ParseException, NonTransientResourceException {
log.info("Reading start... batchRunDate : {}", batchRunDate);
MongoItemReader<ExampleDao> reader = new MongoItemReader<>();
reader.setTemplate(mongoTemplate);
reader.setSort(new HashMap<String, Sort.Direction>() {{
put("_id", Sort.Direction.DESC);
}});
reader.setTargetType(ExampleDao.class);
reader.setQuery("{}");
return reader;
}
}
然后像这样设置一个步骤配置。 (注意 .reader(dataReadExample.read(null))。我期望 @Value("#{[= read() 参数中的 40=]("batchRunDate") 将覆盖 null 值)
@Bean("STEP_FETCH_DATA")
public Step fetchDatabaseStep(
DataReaderExample dataReadExample ,
DataProcessor dataProcessor,
DataWriter dataWriter,
@Qualifier("TASK_EXECUTOR") TaskExecutor taskExecutor
) {
log.info("Initialize step: {}", "STEP_FETCH_DATA");
return stepBuilderFactory.get("STEP_FETCH_DATA")
.<ExampleDao, ExampleDao>chunk(chunkSize)
.processor(dataProcessor)
.reader(dataReadExample.read(null))
.writer(dataWriter)
.taskExecutor(taskExecutor)
.build();
}
My log.info("Reading start... batchRunDate : {}", batchRunDate); 批处理将始终打印为空值和@Value ("#{jobParameters.get("batchRunDate") 不工作。好像我无法访问 jobParameters。
谁能向我解释一下这种行为以及如何将 ItemReader 移动到另一个 class。我的目标是将 ItemReader 分离成另一个 class。谢谢!
您的 DataReaderExample
被声明为 @Component
,它应该是 @Configuration
class,您在其中声明了 bean 定义。
我建议将 read
方法更改为 itemReader
或类似的东西,因为它的目的是定义项目 reader bean 而不是实际读取数据。
完成后,您可以在应用程序上下文中导入 DataReaderExample
配置 class 并在您的步骤中自动装配项目 reader:
@Bean("STEP_FETCH_DATA")
public Step fetchDatabaseStep(
ItemReader<ExampleDao> itemReader ,
DataProcessor dataProcessor,
DataWriter dataWriter,
@Qualifier("TASK_EXECUTOR") TaskExecutor taskExecutor
) {
log.info("Initialize step: {}", "STEP_FETCH_DATA");
return stepBuilderFactory.get("STEP_FETCH_DATA")
.<ExampleDao, ExampleDao>chunk(chunkSize)
.processor(dataProcessor)
.reader(itemReader)
.writer(dataWriter)
.taskExecutor(taskExecutor)
.build();
}