使用带有自动配置和非标准数据库的 Spring Batch [英] Using Spring Batch with auto-configure and a non-standard database

查看:74
本文介绍了使用带有自动配置和非标准数据库的 Spring Batch的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试创建一个 Spring Batch 应用程序.我们使用 SQL Anywhere 数据库,它实际上是一种已知的数据库类型 SQLSERVER.为了让事情更简单,我在主类上使用了 @SpringBootApplication,在配置类上使用了 @EnableBatchProcessing.

I am attempting to create a Spring Batch application. We use a SQL Anywhere database, which is effectively SQLSERVER, a known database type. To make things easier I am using @SpringBootApplication on my main class and @EnableBatchProcessing on my configuration class.

问题是我的数据库驱动程序 sybase.jdbc4.sqlanywhere.IDriver 返回产品名称SQL Anywhere",而 Spring 无法识别该名称,从而导致各种错误.我能够通过在我的配置类中显式创建 JobRepositoryFactoryBean 来绕过其中的一些:

The problem is that my database driver, sybase.jdbc4.sqlanywhere.IDriver, returns a product name "SQL Anywhere" and this is not recognized by Spring, causing various errors. I was able to get past some of them by explicitly creating a JobRepositoryFactoryBean in my configuration class:

/**
 * We can't rely on Spring Boot as it can't set the database type properly.
 * 
 * By explicitly requiring the arguments in the constructor, we force the Autowiring
 * to occur.
 */
@Bean
public JobRepositoryFactoryBean jobRepositoryFactory(DataSource ds, PlatformTransactionManager tm) {
    JobRepositoryFactoryBean jf = new JobRepositoryFactoryBean();

    jf.setDataSource(ds);
    jf.setTransactionManager(tm);
    jf.setDatabaseType("SQLSERVER");
    jf.setTablePrefix("DBA.BATCH_");
    jf.setIsolationLevelForCreate("ISOLATION_SERIALIZABLE");    // only one instance at a time

    return jf;
}

然而,DefaultBatchConfigurer 在初始化函数中失败,因为它显式地构造了自己的 JobExplorerFactoryBean.

However, DefaultBatchConfigurer fails in the intialize function, because it explicitly constructs its own JobExplorerFactoryBean.

我想知道是否有一些简单的方法可以解决这个问题,或者我是否必须复制 DefaultBatchConfigurer 类中的工作并自己定义所有 bean 并删除 @EnableBatchProcessing注释.

I wonder if there is some simple way around this, or if I will have to duplicate the work in the DefaultBatchConfigurer class and define all the beans myself and remove the @EnableBatchProcessing annotation.

推荐答案

我能够解决这个问题,我希望它可以帮助任何尝试将 Spring Batch 与开箱即用的数据库一起使用的人.有必要扩展 DefaultBatchConfigurer 并覆盖 createJobRepository() 函数.此外,您应该禁用自动创建作业表.

I was able to solve this, and I hope it helps anyone trying to use Spring Batch with a database that is out-of-the-box. It is necessary to extend DefaultBatchConfigurer and override the createJobRepository() function. Also, you should disable the automatic job table creation.

这是我创建的类,可用作任何 SQL Anywhere Spring Batch 作业的基础:

Here is the class I created that can be used as a base for any SQL Anywhere Spring Batch job:

@EnableBatchProcessing
public class SqlAnywhereBatchConfigurer extends DefaultBatchConfigurer {

  @Autowired
  private DataSource dataSource;
  @Autowired
  private PlatformTransactionManager transactionManager;

  public SqlAnywhereBatchConfigurer() {
      super();
  }

  public SqlAnywhereBatchConfigurer(DataSource dataSource) {
      super(dataSource);
  }

  @Override
  protected JobRepository createJobRepository() throws Exception {
    JobRepositoryFactoryBean factory = new JobRepositoryFactoryBean();
    factory.setDataSource(dataSource);
    factory.setTransactionManager(transactionManager);
    factory.setDatabaseType("SQLSERVER");
    factory.afterPropertiesSet();
    return factory.getObject();
  }
}

记得先使用 schema-sqlserver.sql 来设置你的表.

Remember to use the schema-sqlserver.sql to set up your tables first.

你必须在你的配置中定义一个数据源,在 application.properties 我有:

You must define a datasource in your configuration, in application.properties I have:

# database
spring.datasource.url=jdbc:sqlanywhere:Server=<your server name>;port=2638
spring.datasource.username=<your username>
spring.datasource.password=<your password>
spring.datasource.driver-class-name=sybase.jdbc4.sqlanywhere.IDriver
# don't create tables on startup
spring.datasource.initialize=false
spring.batch.initializer.enabled=false

最后,这里值得一提的是,对于 SQL Anywhere 至少 JdbcCursorItemReader 不起作用,因为设置准备好的语句的获取方向会导致不支持"SQL Exception 被抛出.您可以通过扩展 JdbcCursorItemReader 并覆盖您自己的类中的 applyStatementSettings 函数(加上一些 setter)来解决这个问题.

Finally, it is worth mentioning here that for SQL Anywhere at least the JdbcCursorItemReader does not work, because setting the fetch direction of the prepared statement causes a "not supported" SQL Exception to be thrown. You can get around this by extending JdbcCursorItemReader and overriding the applyStatementSettings function (plus a few setters) in your own class.

这篇关于使用带有自动配置和非标准数据库的 Spring Batch的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆