如何为Spring Batch JUnit 5测试成功加载Spring任务的JobLauncherTestUtils类

BreenDeen:

我有一个看似简单的配置用于春季批测试。但是,测试无法加载上下文。该错误告诉我,有一个与数据源有关的无法解析的循环引用。如果删除数据源,该错误将更改为未定义数据源。我要做的就是能够加载JobLauncherTestUtils,然后启动一项作业来测试步骤。看起来很简单,但要加载简单的测试作业却非常困难。我正在Java 12和spring 5以及spring batch 2.2.0.RELEASE和JUnit 5(Jupiter)上运行spring boot 2。配置有什么问题?我需要进行哪些更改。我认为您不一定必须指定一个数据源配置,但是如果不进行配置,它就不会接近加载。这是我的配置。我非常感谢您提供一些帮助,以弄清我的配置出了什么问题。我的目标仅仅是成功地自动装配JobLauncherTestUtils类。

like 

class BatchTest {
   @Autowired
   JobLauncherTestUtils jobLauncherTestUtils;
}


import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.ExtendWith;
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.core.launch.JobLauncher;
import org.springframework.batch.core.launch.support.RunIdIncrementer;
import org.springframework.batch.core.launch.support.SimpleJobLauncher;
import org.springframework.batch.core.repository.support.JobRepositoryFactoryBean;
import org.springframework.batch.test.JobLauncherTestUtils;
import org.springframework.batch.test.context.SpringBatchTest;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.batch.BatchAutoConfiguration;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.jdbc.datasource.embedded.EmbeddedDatabase;
import org.springframework.jdbc.datasource.embedded.EmbeddedDatabaseBuilder;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.TestPropertySource;
import org.springframework.test.context.junit.jupiter.SpringExtension;


@ExtendWith(SpringExtension.class)
@SpringBatchTest
@ContextConfiguration(classes = {BatchTest.BatchConfiguration.class, 
BatchAutoConfiguration.class})
@TestPropertySource(properties = "debug=true")
public class BatchTest {

@Autowired
private JobLauncherTestUtils jobLauncherTestUtils;

@Test
public void test() {
    this.jobLauncherTestUtils.launchStep("orderProcessingJob");
    //assertions 
}

    @Configuration
    @EnableBatchProcessing
    public static class BatchConfiguration {

    private  JobBuilderFactory jobBuilderFactory;

    @Bean(name="jobLauncherTestUtils")
    public JobLauncherTestUtils jobLauncherTestUtils() throws Exception {
        JobLauncherTestUtils jl = new JobLauncherTestUtils();
        jl.setJobLauncher(jobLauncher());
        jl.setJob(orderProcessorJob());
        jl.setJobRepository(jobRepository().getObject());
        return jl;
    }

        @Bean
        public JobRepositoryFactoryBean jobRepository() {
        JobRepositoryFactoryBean jobRepositoryFactoryBean = new JobRepositoryFactoryBean();
        jobRepositoryFactoryBean.setDataSource(dataSource());
        return jobRepositoryFactoryBean;
      }


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

    private Step orderIntakeStep() {
        // code for order Intake
    }

    @Bean
    public JobLauncher jobLauncher() throws Exception {
        SimpleJobLauncher jobLauncher = new SimpleJobLauncher();
        jobLauncher.setJobRepository(jobRepository().getObject());
        return jobLauncher;
    }


    private  StepBuilderFactory stepBuilderFactory;


    @Bean
    public EmbeddedDatabase dataSource() {
        return new EmbeddedDatabaseBuilder().build();
    }


    @Autowired
    public BatchConfiguration(JobBuilderFactory jobBuilderFactory , 
                                          StepBuilderFactory stepBuilderFactory) {
        this.jobBuilderFactory = jobBuilderFactory;
        this.stepBuilderFactory = stepBuilderFactory;
     }

    }
 }

这是我所看到的stacktrace的核心部分:

由以下原因引起:org.springframework.beans.factory.UnsatisfiedDependencyException:创建名称为'batchTest.BatchConfiguration'的bean时出错:

通过构造函数参数0表示的不满足的依赖关系;嵌套异常

是org.springframework.beans.factory.UnsatisfiedDependencyException:创建名称为“ org.springframework.batch.core.configuration.annotation.SimpleBatchConfiguration”的bean时出错:

通过字段“ dataSource”表示不满意的依赖关系;嵌套的异常是org.springframework.beans.factory.BeanCurrentlyInCreationException:

创建名称为'batchTest.BatchConfiguration'的bean时出错:当前正在创建请求的bean:是否存在不可解析的循环引用?

Mahmoud Ben Hassine:

通过字段“ dataSource”表示不满意的依赖关系;嵌套的异常是org.springframework.beans.factory.BeanCurrentlyInCreationException:

创建名称为'batchTest.BatchConfiguration'的bean时出错:当前正在创建请求的bean:是否存在不可解析的循环引用?

您要注入的数据源BatchConfiguration#jobRepository()是在同一类(dataSource()方法)中创建的,因此会出现错误。您需要将数据源配置提取到一个单独的类中,例如:

@Configuration
public static class DataSourceConfig {
   @Bean
   public EmbeddedDatabase dataSource() {
      return new EmbeddedDatabaseBuilder().build();
   }
}

然后将其导入您的BatchConfiguration

@Configuration
@Import(DataSourceConfig.class)
@EnableBatchProcessing
public static class BatchConfiguration {

   // ..       

   @Bean
   public JobRepositoryFactoryBean jobRepository(DataSource dataSource) {
      JobRepositoryFactoryBean jobRepositoryFactoryBean = new JobRepositoryFactoryBean();
      jobRepositoryFactoryBean.setDataSource(dataSource);
       return jobRepositoryFactoryBean;
  }
  
  // ..
}

我建议将基础结构Bean与业务逻辑Bean分开。就是说,由于您正在使用@EnableBatchProcessing,因此无需自己配置作业存储库,作业启动器等。此注释的目的是为您提供那些基础结构bean,请参阅其javadoc

我的目标仅仅是成功地自动装配JobLauncherTestUtils类。

由于正在使用@SpringBatchTest,因此无需JobLauncherTestUtils手动创建(在您的jobLauncherTestUtils()方法中),此注释的目标是为您导入它,请参阅其Javadoc这是典型用法:

@RunWith(SpringRunner.class)
@SpringBatchTest
@ContextConfiguration(classes = MyBatchJobConfiguration.class)
public class MyBatchJobTests {

    @@Autowired
    private JobLauncherTestUtils jobLauncherTestUtils;

    @@Autowired
    private JobRepositoryTestUtils jobRepositoryTestUtils;

    @Before
    public void clearJobExecutions() {
        this.jobRepositoryTestUtils.removeJobExecutions();
    }

    @Test
    public void testMyJob() throws Exception {
        // given
        JobParameters jobParameters = this.jobLauncherTestUtils.getUniqueJobParameters();

        // when
        JobExecution jobExecution = this.jobLauncherTestUtils.launchJob(jobParameters);

        // then
        Assert.assertEquals(ExitStatus.COMPLETED, jobExecution.getExitStatus());
    }

}

本文收集自互联网,转载请注明来源。

如有侵权,请联系 [email protected] 删除。

编辑于
0

我来说两句

0 条评论
登录 后参与评论

相关文章

来自分类Java

如何为Spring Batch配置分配动态属性?

来自分类Java

如何为Spring Boot应用程序编写Junit测试用例?

来自分类Java

如何为通过Spring注入的mapstruct抽象映射器编写Junit测试

来自分类Dev

如何为自定义Spring Batch阅读器编写Junits

来自分类Java

如何为DirectoryStream编写JUnit测试

来自分类Java

如何为JUnit测试案例禁用EhCache

来自分类Dev

如何为Spring Integration DSL Http.outboundGateway操作编写JUnit

来自分类Java

如何为使用网络连接的类编写jUnit测试

来自分类Dev

Junit 5:如何为参数化测试提供名称

来自分类Java

Spring RestController + Junit测试

来自分类Java

如果出现异常,如何为委托编写者重写Spring Batch CompositeItemWriter管理事务?

来自分类Java

如何在Spring Boot JUnit测试中排除* AutoConfiguration类?

来自分类Java

使用Mockito和jUnit5的SpringBoot Controller测试失败,因为Spring无法创建可加载属性的PropertyService类的bean?

来自分类Java

如何使用JUnit在Spring中测试ConfigurationProperties?

来自分类Java

如何用Spring Autowire编写JUnit测试?

来自分类Java

如何从jUnit测试访问Spring @Service对象

来自分类Dev

如何在用Kotlin编写的JUnit 5测试类中注入Spring bean?

来自分类Java

如何为打印“ Hello,World!”的主要方法编写Junit 字符串到控制台并使用Spring Framework

来自分类Dev

如何在Spring Test Suite中运行JUnit 5测试?

来自分类Dev

如何测试JUnit Jupiter(JUnit 5)扩展

来自分类Java

如何为JUnit测试用例运行启用全局超时?

来自分类Java

如何为Junit单元测试设置JVM参数?

来自分类Java

如何为不同的JUnit测试集设置多个设置?

来自分类Dev

如何为junit测试实例化Mock Kafka主题?

来自分类Java

如何为空函数Pointcut编写JUnit测试

来自分类Java

如何为线程运行方法编写junit测试用例

来自分类Java

如何为调用API的方法编写JUnit测试?

来自分类Java

Spring JUnit 5测试中的异常

来自分类Java

JavaMailSender设置Spring Batch

TOP 榜单

热门标签

归档