Spring-Batch @BeforeStep不适用于@StepScope

我正在使用Spring Batch版本2.2.4.RELEASE我试图用有状态的ItemReader,ItemProcessor和ItemWriter Bean编写一个简单的示例。

public class StatefulItemReader implements ItemReader<String> {

private List<String> list;

@BeforeStep

public void initializeState(StepExecution stepExecution) {

this.list = new ArrayList<>();

}

@AfterStep

public ExitStatus exploitState(StepExecution stepExecution) {

System.out.println("******************************");

System.out.println(" READING RESULTS : " + list.size());

return stepExecution.getExitStatus();

}

@Override

public String read() throws Exception {

this.list.add("some stateful reading information");

if (list.size() < 10) {

return "value " + list.size();

}

return null;

}

}

在集成测试中,我在内部静态java config类中声明我的bean,如下所示:

@ContextConfiguration

@RunWith(SpringJUnit4ClassRunner.class)

public class SingletonScopedTest {

@Configuration

@EnableBatchProcessing

static class TestConfig {

@Autowired

private JobBuilderFactory jobBuilder;

@Autowired

private StepBuilderFactory stepBuilder;

@Bean

JobLauncherTestUtils jobLauncherTestUtils() {

return new JobLauncherTestUtils();

}

@Bean

public DataSource dataSource() {

EmbeddedDatabaseBuilder embeddedDatabaseBuilder = new EmbeddedDatabaseBuilder();

return embeddedDatabaseBuilder.addScript("classpath:org/springframework/batch/core/schema-drop-hsqldb.sql")

.addScript("classpath:org/springframework/batch/core/schema-hsqldb.sql")

.setType(EmbeddedDatabaseType.HSQL)

.build();

}

@Bean

public Job jobUnderTest() {

return jobBuilder.get("job-under-test")

.start(stepUnderTest())

.build();

}

@Bean

public Step stepUnderTest() {

return stepBuilder.get("step-under-test")

.<String, String>chunk(1)

.reader(reader())

.processor(processor())

.writer(writer())

.build();

}

@Bean

public ItemReader<String> reader() {

return new StatefulItemReader();

}

@Bean

public ItemProcessor<String, String> processor() {

return new StatefulItemProcessor();

}

@Bean

public ItemWriter<String> writer() {

return new StatefulItemWriter();

}

}

@Autowired

JobLauncherTestUtils jobLauncherTestUtils;

@Test

public void testStepExecution() {

JobExecution jobExecution = jobLauncherTestUtils.launchStep("step-under-test");

assertEquals(ExitStatus.COMPLETED, jobExecution.getExitStatus());

}

}

该测试通过。

但是,一旦我将StatefulItemReader定义为步域范围的bean(这对于有状态阅读器比较好),就不再执行“步骤前”代码。

...

@Bean

@StepScope

public ItemReader<String> reader() {

return new StatefulItemReader();

}

...

而且我注意到处理器和我的编写器bean存在相同的问题。

回答:

当你按如下方式配置bean时:

@Bean

@StepScope

public MyInterface myBean() {

return new MyInterfaceImpl();

}

你正在告诉Spring使用代理模式ScopedProxyMode.TARGET_CLASS。但是,通过返回MyInterface而不是返回,MyInterfaceImpl代理仅具有对上方法的可见性MyInterface。这将阻止Spring Batch能够在MyInterfaceImpl已使用侦听器注释(例如)进行注释的方法上找到方法@BeforeStep。正确MyInterfaceImpl的配置方法是返回你的配置方法,如下所示:

@Bean

@StepScope

public MyInterfaceImpl myBean() {

return new MyInterfaceImpl();

}

我们在启动时添加了一条警告日志消息,该消息指出,当我们寻找带注释的侦听器方法时,如果该对象被代理并且目标是接口,则将无法在实现类上找到带有注释的方法他们。

以上是 Spring-Batch @BeforeStep不适用于@StepScope 的全部内容, 来源链接: utcz.com/qa/435928.html

回到顶部