4

I'm working on a Spring Boot/Spring Batch project, and I need to configure two data sources. One is an in-memory hsqldb database used for tracking transactions. The other is a regular MySQL database which will be updated by my ItemWriters.

The problem is that as soon as I try to configure the second datasource, Spring starts throwing 'unresolvable circular dependency' errors, i.e.

Error creating bean with name 'preprodDataSource' defined in class path 
resource [xxx/tools/batch/xxx/MyConfiguration.class]: Initialization of
bean failed; nested exception is 
org.springframework.beans.factory.BeanCurrentlyInCreationException: Error 
creating bean with name 'dataSourceAutoConfigurationInitializer': Requested bean is 
currently in creation: Is there an unresolvable circular reference?

The relevant chunk of my MyConfiguration.java file looks like:

@Bean
public DataSource transactionsDataSource() {
    BasicDataSource dataSource = new BasicDataSource();
    dataSource.setDriverClassName("org.hsqldb.jdbcDriver");
    dataSource.setUrl("jdbc:hsqldb:mem:testdb;sql.enforce_strict_size=true;hsqldb.tx=mvcc");
    dataSource.setUsername("sa");
    dataSource.setPassword("");
    return dataSource;
}

@Bean
public DataSource preprodDataSource() {
    BasicDataSource dataSource = new BasicDataSource();
    dataSource.setDriverClassName("com.mysql.jdbc.Driver");
    dataSource.setUrl("jdbc:mysql://localhost:3306/somedb");
    dataSource.setUsername("someuser");
    dataSource.setPassword("somepass");
    return dataSource;
}

If I comment out the @Bean defining the second data source, everything is fine. The application starts up and runs without problems. However, if I leave it in, I get the error above.

My naive interpretation of this is that Spring is building an instance of 'dataSourceAutoConfigurationInitializer' to handle initialization of the first datasource and that when it tries to construct a second to handle the second datasource, bad things happen.

Is there any way to work around this?

slamci
  • 424
  • 1
  • 5
  • 13
  • I'm guessing it might relate to the fact that both of your `DataSource` beans qualify for injection, so things go awry. You may need to move away from letting Spring Boot do its auto-config, in which case, this may be useful: http://stackoverflow.com/questions/15008809/multiple-jparepositories-in-xml-config-how-to-configure-with-enablejpareposit/19976132#19976132 – Steve Jul 17 '14 at 08:22
  • Here is a good example on [how to configure jpa repositories using different datasource and transaction manager](http://www.baeldung.com/spring-data-jpa-multiple-databases) – Eduardo Sanchez-Ros Jan 14 '16 at 14:43

1 Answers1

2

By default, Spring Boot's auto-configuration will try to create a JdbcTemplate for you using your application's DataSource. As you have configured two, it doesn't know which one to use. To tell it which one to use you should mark one of them as @Primary:

@Bean
@Primary
public DataSource transactionsDataSource() {
    BasicDataSource dataSource = new BasicDataSource();
    …
    return dataSource;
}

Alternatively, you could disable the auto-configuration.

Andy Wilkinson
  • 108,729
  • 24
  • 257
  • 242