You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Spring中如何使用spring-batch-excel的PoiItemReader Bean读取Excel数据?

How to Use the PoiItemReader Bean in Your Custom Class

Hey there! Let's walk through how to use that PoiItemReader bean you've configured, since you're new to Spring and Spring Batch. First off, don't call the excelReader() method directly—that would create a new instance instead of using the one Spring's container manages for you. Here's what to do instead:

1. Inject the PoiItemReader into Your Custom Class

Use Spring's dependency injection to get the pre-configured PoiItemReader bean into your own reader class. Constructor injection is the recommended approach—it's safer and easier to test:

import org.springframework.batch.item.excel.poi.PoiItemReader;
import org.springframework.stereotype.Component;
import java.util.ArrayList;
import java.util.List;

@Component
public class YourCustomReader {

    private final PoiItemReader excelReader;

    // Spring automatically passes the PoiItemReader bean here
    public YourCustomReader(PoiItemReader excelReader) {
        this.excelReader = excelReader;
    }

    // Methods to read Excel data will go here
}

2. Read Excel Rows Using the Injected Reader

The PoiItemReader implements Spring Batch's ItemReader interface, which has a read() method. This method returns one row of data at a time (as an Object[] since you're using PassThroughRowMapper) and returns null when there are no more rows left.

To collect all rows into a list, loop through the read() method like this:

public List<Object[]> getAllExcelRows() throws Exception {
    List<Object[]> allRows = new ArrayList<>();
    Object[] currentRow;

    // Keep reading until read() returns null (end of the Excel file)
    while ((currentRow = (Object[]) excelReader.read()) != null) {
        allRows.add(currentRow);
    }

    return allRows;
}

Note on PassThroughRowMapper

Since you're using PassThroughRowMapper, each Excel row is converted directly into an Object[] where each element maps to a cell's value. If you later switch to a custom RowMapper that maps rows to your own entity class (e.g., Customer), the read() method will return instances of that class instead.

While manual read() calls work for small tasks, Spring Batch is built to handle end-to-end batch processing with Jobs and Steps. Here's a quick example of wiring your PoiItemReader into a full batch job:

import org.springframework.batch.core.Job;
import org.springframework.batch.core.Step;
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.item.ItemWriter;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import java.util.Arrays;

@Configuration
@EnableBatchProcessing
public class BatchConfig {

    private final JobBuilderFactory jobBuilderFactory;
    private final StepBuilderFactory stepBuilderFactory;
    private final PoiItemReader excelReader;

    public BatchConfig(JobBuilderFactory jobBuilderFactory, StepBuilderFactory stepBuilderFactory, PoiItemReader excelReader) {
        this.jobBuilderFactory = jobBuilderFactory;
        this.stepBuilderFactory = stepBuilderFactory;
        this.excelReader = excelReader;
    }

    @Bean
    public Step excelProcessingStep(ItemWriter<Object[]> excelWriter) {
        return stepBuilderFactory.get("excelProcessingStep")
                .<Object[], Object[]>chunk(10) // Process 10 rows at a time
                .reader(excelReader)
                .writer(excelWriter)
                .build();
    }

    @Bean
    public ItemWriter<Object[]> excelWriter() {
        return items -> {
            // Process rows here (e.g., save to database, transform data)
            for (Object[] row : items) {
                System.out.println("Processing row: " + Arrays.toString(row));
            }
        };
    }

    @Bean
    public Job excelImportJob(Step excelProcessingStep) {
        return jobBuilderFactory.get("excelImportJob")
                .start(excelProcessingStep)
                .build();
    }
}

You can launch this job using a JobLauncher on application start, or expose an endpoint to trigger it manually if you're using Spring Boot.


内容的提问来源于stack exchange,提问作者Avi Rudich

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.15 03:33:46