在Spring Boot和Batch项目中设置DataSource时,BeanCurrentlyInCreationException

时间:2018-07-24 23:18:41

标签: java spring-boot spring-batch datasource

我在maven多模块项目中同时使用Spring Boot和Batch来解析CSV文件并将数据存储在MySQL数据库中。

使用我的BatchLauncher类(在下面共享)运行批处理模块时,我得到了由BeanCurrentlyInCreationException引起的getDataBase(),它用于配置MySQL数据库。 (点击此link查看日志)

当我删除此方法时,Spring Boot会自动选择一个H2类型的嵌入式数据库(link用于日志)

BatchLauncher类:

@Slf4j
public class BatchLauncher {

    public static void main(String[] args) {
        try {
            Launcher.launchWithConfig("My Batch", BatchConfig.class, false);
        }catch (Exception ex) {
        log.error(ex.getMessage());
        }
    }
}

发射器类:

@Slf4j
public class Launcher {

    private Launcher() {}

    public static void launchWithConfig(String batchName, Class<?> configClass, boolean oncePerDayMax) throws JobExecutionException, BatchException {
        try {
            // Check the spring profiles used
            log.info("Start batch \"" + batchName + "\" with profiles : " + System.getProperty("spring.profiles.active"));

            // Load configuration
            @SuppressWarnings("resource")
            AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(configClass);

            JobLauncher jobLauncher = context.getBean(JobLauncher.class);
            Job job = context.getBean(Job.class);

            //Authorize only one execution of each job per day
            JobParameters jobParameters = new JobParameters();
            JobExecution execution = jobLauncher.run(job, jobParameters);

            if(!BatchStatus.COMPLETED.equals(execution.getStatus())) {
                throw new BatchException("Unknown error while executing batch : " + batchName);
            }
        }catch (Exception ex){
            log.error("Exception",ex);
            throw new BatchException(ex.getMessage());
        }
    }
}

BatchConfig类:

@Slf4j
@Configuration
@EnableAutoConfiguration(exclude = {DataSourceAutoConfiguration.class, DataSourceTransactionManagerAutoConfiguration.class, HibernateJpaAutoConfiguration.class})
@EnableBatchProcessing
@ComponentScan(basePackages = {
        "fr.payet.flad.batch.tasklet",
        "fr.payet.flad.batch.mapper"
})
@Import({CoreConfig.class})
public class BatchConfig {


    private StepBuilderFactory steps;
    private JobBuilderFactory jobBuilderFactory;
    private ReadInputTasklet readInputTasklet;

    public BatchConfig(StepBuilderFactory steps, JobBuilderFactory jobBuilderFactory, ReadInputTasklet readInputTasklet) {
        this.steps = steps;
        this.jobBuilderFactory = jobBuilderFactory;
        this.readInputTasklet = readInputTasklet;
    }

    @Bean
    public DataSource getDataBase(){
        return DataSourceBuilder
                .create()
                .driverClassName("com.mysql.jdbc.Driver")
                .url("jdbc:mysql://localhost:3306/myDb?useSSL=false")
                .username("myuser")
                .password("mypwd")
                .build();
    }

    @Bean
    public Step readInputStep() {
        return steps.get("readInputStep")
                .tasklet(readInputTasklet)
                .build();
    }

    @Bean
    public Job readCsvJob() {
        return jobBuilderFactory.get("readCsvJob")
                .incrementer(new RunIdIncrementer())
                .flow(readInputStep())
                .end()
                .build();
    }
}

1 个答案:

答案 0 :(得分:0)

解决方案是创建一个用DataSourceConfiguration注释的自定义@Configuration类,在其中我这样设置自己的数据库:

@Bean
public DataSource getDataBase(){
    return DataSourceBuilder
            .create()
            .driverClassName("com.mysql.jdbc.Driver")
            .url("jdbc:mysql://localhost:3306/myDB?useSSL=false")
            .username("myUser")
            .password("myPwd")
            .build();
}