首页 > 解决方案 > 由于 JDBC 异常而无法运行 Batch Job

问题描述

我已经使用数据源和事务管理器设置了批处理配置。为此,我必须覆盖默认配置器。但是在尝试从测试中运行作业时,由于 jdbc 异常而无法启动。它似乎无法初始化元表。

这是批处理的配置

@Autowired
private JobBuilderFactory jobBuilderFactory;

@Autowired
private StepBuilderFactory stepBuilderFactory;


@Bean
public BatchConfigurer batchConfigurer(DataSource dataSource,
                                       JpaTransactionManager jpaTransactionManager) {
    return new DefaultBatchConfigurer(dataSource) {
        @Override
        public PlatformTransactionManager getTransactionManager() {
            return jpaTransactionManager;
        }
    };
}

这是JPA的配置

@Bean
public DataSource dataSource() {
    final DriverManagerDataSource dataSource = new DriverManagerDataSource();
    dataSource.setDriverClassName(datasourceEnv.getProperty("jdbc.driverClassName"));
    dataSource.setUrl(datasourceEnv.getProperty("jdbc.url"));
    dataSource.setUsername(datasourceEnv.getProperty("jdbc.username"));
    dataSource.setPassword(datasourceEnv.getProperty("jdbc.password"));
    return dataSource;
}

public LocalContainerEntityManagerFactoryBean entityManagerFactory() {
    final LocalContainerEntityManagerFactoryBean em = new LocalContainerEntityManagerFactoryBean();
    em.setDataSource(dataSource());
    em.setPackagesToScan("my.repository");
    em.setJpaVendorAdapter(new HibernateJpaVendorAdapter());
    em.setJpaProperties(additionalProperties());
    return em;
}

@Bean
JpaTransactionManager transactionManager(final EntityManagerFactory entityManagerFactory) {
    final JpaTransactionManager transactionManager = new JpaTransactionManager();
    transactionManager.setEntityManagerFactory(entityManagerFactory);
    return transactionManager;
}

private Properties additionalProperties() {
    final Properties hibernateProperties = new Properties();
    hibernateProperties.setProperty("hibernate.hbm2ddl.auto", datasourceEnv.getProperty("hibernate.hbm2ddl.auto"));
    hibernateProperties.setProperty("hibernate.dialect", datasourceEnv.getProperty("hibernate.dialect"));
    hibernateProperties.setProperty("hibernate.show_sql", datasourceEnv.getProperty("hibernate.show_sql"));
    return hibernateProperties;
}

这是输出中的异常

Caused by: org.h2.jdbc.JdbcSQLException: Table "BATCH_JOB_INSTANCE" 
not found; SQL statement:
SELECT JOB_INSTANCE_ID, JOB_NAME from BATCH_JOB_INSTANCE where 
JOB_NAME = ? and JOB_KEY = ? [42102-197]
    at 
org.h2.message.DbException.getJdbcSQLException(DbException.java:357)
at org.h2.message.DbException.get(DbException.java:179)
at org.h2.message.DbException.get(DbException.java:155)
at org.h2.command.Parser.readTableOrView(Parser.java:5920)
at org.h2.command.Parser.readTableFilter(Parser.java:1430)
at 
org.h2.command.Parser.parseSelectSimpleFromPart(Parser.java:2138)
at org.h2.command.Parser.parseSelectSimple(Parser.java:2287)
at org.h2.command.Parser.parseSelectSub(Parser.java:2133)
at org.h2.command.Parser.parseSelectUnion(Parser.java:1946)
at org.h2.command.Parser.parseSelect(Parser.java:1919)
at org.h2.command.Parser.parsePrepared(Parser.java:463)
at org.h2.command.Parser.parse(Parser.java:335)
at org.h2.command.Parser.parse(Parser.java:307)
at org.h2.command.Parser.prepareCommand(Parser.java:278)
at org.h2.engine.Session.prepareLocal(Session.java:611)
at org.h2.engine.Session.prepareCommand(Session.java:549)
at 
org.h2.jdbc.JdbcConnection.prepareCommand(JdbcConnection.java:1247)
at org.h2.jdbc.JdbcPreparedStatement.<init>
(JdbcPreparedStatement.java:76)
at 
org.h2.jdbc.JdbcConnection.prepareStatement(JdbcConnection.java:304)
at 
... 68 more

我尝试通过添加带有数据库 url 的 runscript。但在这种情况下,会产生反向错误。然后它说表已经存在。

Caused by: org.h2.jdbc.JdbcSQLException: Table "BATCH_JOB_INSTANCE" 
already exists; SQL statement:
-- Autogenerated: do not edit this file

CREATE TABLE BATCH_JOB_INSTANCE  (
JOB_INSTANCE_ID BIGINT IDENTITY NOT NULL PRIMARY KEY ,
VERSION BIGINT ,
JOB_NAME VARCHAR(100) NOT NULL,
JOB_KEY VARCHAR(32) NOT NULL,
constraint JOB_INST_UN unique (JOB_NAME, JOB_KEY)
)  [42101-197]
at 
org.h2.message.DbException.getJdbcSQLException(DbException.java:357)
at org.h2.message.DbException.get(DbException.java:179)
at org.h2.message.DbException.get(DbException.java:155)
at org.h2.command.ddl.CreateTable.update(CreateTable.java:86)

这是数据源配置

jdbc.driverClassName=org.h2.Driver
jdbc.url=jdbc:h2:mem:db;DB_CLOSE_DELAY=-1
jdbc.username=sa
jdbc.password=
hibernate.dialect=org.hibernate.dialect.H2Dialect
hibernate.show_sql=true
hibernate.hbm2ddl.auto=create-drop

这是 application.properties

spring.batch.initialize-schema=always

是的,application.properties 在这个目录下

src/test/resources/application.properties

这是批量测试

@RunWith(SpringRunner.class)
@ContextConfiguration(classes = {ArticleBatchConfiguration.class, 
JobLauncherTestUtils.class, JPAConfig.class})
public class BatchTest {


   @Autowired
   private JobLauncherTestUtils jobLauncherTestUtils;

   @Autowired
   private CustomerRepository customerRepository;

   @Test
   public void givenChunksJob_WhenJobEnds_ThenStatusCompleted() throws 
   Exception {
        JobExecution jobExecution = jobLauncherTestUtils.launchJob();
        Assert.assertEquals(ExitStatus.COMPLETED, 
           jobExecution.getExitStatus());
        List<Customer> customers = customerRepository.findAll();
        Assert.assertThat(customers.size(), Is.is(2));
   }
}

标签: spring-batch

解决方案


推荐阅读