簡體   English   中英

Java Spring 批處理 - 資源文件未注入到 tasklet

[英]Java Spring Batch - Resource file is not injected into the tasklet

我正在執行 Spring 批處理第 1 章中的 java 示例。在此示例中,tasket 解壓縮 zip 文件。 tasklet 接收 zip 文件路徑作為作業參數。 我實現了一個運行作業並傳遞參數的測試方法。

@StepScope
@Component
public class DecompressTasklet implements Tasklet {

    private static final Logger LOGGER = LogManager.getLogger(DecompressTasklet.class);

    @Value("#{jobParameters['inputResource']}")
    private Resource inputResource;

    @Value("#{jobParameters['targetDirectory']}")
    private String targetDirectory;

    @Value("#{jobParameters['targetFile']}")
    private String targetFile;

    @Override
    public RepeatStatus execute(StepContribution contribution, ChunkContext chunkContext) throws Exception {
        //code here
    }
}   

@Configuration
public class DescompressStep {

    @Autowired
    private StepBuilderFactory stepBuilderFactory;

    @Autowired
    private DecompressTasklet decompressTasklet;

    @Bean
    public Step stepDescompress() {
        return stepBuilderFactory
                .get(DescompressStep.class.getSimpleName())
                .tasklet(decompressTasklet)
                .build();

    }
}

@EnableBatchProcessing
@Configuration
public class ImportProductsJob {

    @Autowired
    private DescompressStep descompressStep;

    @Autowired
    private ReadWriteProductStep readWriteProductStep;

    @Bean
    public Job job(JobBuilderFactory jobBuilderFactory) {

        return jobBuilderFactory
                .get("importProductsJob")
                .start(descompressStep.stepDescompress())
                .next(readWriteProductStep.stepReaderWriter())
                .incrementer(new RunIdIncrementer())
                .build();
    }


}

下面是運行作業的測試代碼

@RunWith(SpringRunner.class)
@SpringBootTest
@SpringBatchTest
@AutoConfigureTestDatabase
public class ImportProductsIntegrationTest {

    @Autowired
    private JobRepositoryTestUtils jobRepositoryTestUtils;  

    @Autowired
    private JobLauncherTestUtils jobLauncherTestUtils;  

    @After
    public void cleanUp() {
        jobRepositoryTestUtils.removeJobExecutions();
    }

    @Test
    public void importProducts() throws Exception {
        jobLauncherTestUtils.launchJob(defaultJobParameters());
    }

    private JobParameters defaultJobParameters() {
        JobParametersBuilder paramsBuilder = new JobParametersBuilder();
        paramsBuilder.addString("inputResource", "classpath:input/products.zip");
        paramsBuilder.addString("targetDirectory", "./target/importproductsbatch/");
        paramsBuilder.addString("targetFile", "products.txt");
        paramsBuilder.addLong("timestamp", System.currentTimeMillis());
        return paramsBuilder.toJobParameters();
   }

}

products.zip 文件在 src/main/resources/input 問題是運行測試時出現錯誤

java.lang.NullPointerException: null
    at com.springbatch.inaction.ch01.DecompressTasklet.execute(DecompressTasklet.java:62) ~[classes/:na]

我驗證了 inputResource 屬性是 null。 為什么會出現這個錯誤?

在你的工作定義中,你有:

@Bean
public Job job(JobBuilderFactory jobBuilderFactory) {

    return jobBuilderFactory
            .get("importProductsJob")
            .start(descompressStep.stepDescompress())
            .next(readWriteProductStep.stepReaderWriter())
            .incrementer(new RunIdIncrementer())
            .build();
}

您通過步驟startnext方法的方式不正確(我什至不知道這將如何編譯)。 您可以做的是導入步驟配置類並將這兩個步驟都注入到您的作業定義中。 就像是:

@EnableBatchProcessing
@Configuration
@Import({DescompressStep.class, ReadWriteProductStep.class})
public class ImportProductsJob {

    @Bean
    public Job job(JobBuilderFactory jobBuilderFactory,
                   Step stepDescompress, Step stepReaderWriter) {

        return jobBuilderFactory
                .get("importProductsJob")
                .start(stepDescompress)
                .next(stepReaderWriter)
                .incrementer(new RunIdIncrementer())
                .build();
    }

}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM