Spring Boot - 如何配置多个数据源

3

我将尝试使用Spring Boot设置多个数据源(MySql,Postgres和Oracle),并且不使用JPA,而是使用JdbcTemplate。

我已经尝试过以下设置:

application.properties

spring.datasource.test-oracle.username=test-oracle
spring.datasource.test-oracle.password=test-password
spring.datasource.test-oracle.url=dburl/test
spring.datasource.test-oracle.driver-class-name=oracle.jdbc.OracleDriver

spring.datasource.int-oracle.username=int-oracle
spring.datasource.int-oracle.password=int-password
spring.datasource.int-oracle.url=dburl/int
spring.datasource.int-oracle.driver-class-name=oracle.jdbc.driver.OracleDriver

spring.datasource.d.int-mysql.username=user
spring.datasource.d.int-mysql.password=password
spring.datasource.d.int-mysql.url=dburl/d
spring.datasource.d.int-mysql.driver-class-name=com.mysql.jdbc.Driver

spring.datasource.m.int-mysql.username=user
spring.datasource.m.int-mysql.password=password
spring.datasource.m.int-mysql.url=dburl/m
spring.datasource.m.int-mysql.driver-class-name=com.mysql.jdbc.Driver

spring.datasource.d.test-mysql.username=user
spring.datasource.d.test-mysql.password=password
spring.datasource.d.test-mysql.url=dburl/d
spring.datasource.d.test-mysql.driver-class-name=com.mysql.jdbc.Driver

spring.datasource.m.test-mysql.username=user
spring.datasource.m.test-mysql.password=password
spring.datasource.m.test-mysql.url=dburl/m
spring.datasource.m.test-mysql.driver-class-name=com.mysql.jdbc.Driver

MySqlConfiguration.java

@Configuration
public class MySqlConfiguration() {

   @Bean(name = "dMySql")
   @ConfigurationProperties(prefix = "spring.datasource.d.int-mysql")
   public DataSource mysqlDrupalDataSource() {
     return DataSourceBuilder.create().build();
   }

   @Bean(name = "dJdbc")
   public JdbcTemplate drupalJdbcTemplate(DataSource dMySql) {
      return new JdbcTemplate(dMySql);
   }

   @Bean(name = "mMySql")
   @ConfigurationProperties(prefix = "spring.datasource.m.int-mysql")
   public DataSource mysqlDrupalDataSource() {
      return DataSourceBuilder.create().build();
   }

   @Bean(name = "mJdbc")
   public JdbcTemplate drupalJdbcTemplate(DataSource mMySql) {
      return new JdbcTemplate(mMySql);
   }
}

OracleConfiguration.java

@Configuration
public class OracleConfiguration {

   @Primary
   @Bean(name = "tOracle")
   @ConfigurationProperties(prefix = "spring.datasource.test-oracle")
   public DataSource heOracleDataSource() {
      return DataSourceBuilder.create().build();
   }

   @Bean(name = "tOracleJdbc")
   public JdbcTemplate jdbcTemplate(DataSource tOracle) {
      return new JdbcTemplate(tOracle);
   }

   @Bean(name = "iOracle")
   @ConfigurationProperties(prefix = "spring.datasource.int-oracle")
   public DataSource heOracleDataSource() {
      return DataSourceBuilder.create().build();
   }

   @Bean(name = "iOracleJdbc")
   public JdbcTemplate jdbcTemplate(DataSource iOracle) {
      return new JdbcTemplate(iOracle);
   }
}

我不确定上述方法是否正确。根据 Spring Boot 文档,当我使用 @Primary 注解时,带有 @Primary 注解的 Bean 将始终被使用。然后我在 DAO 实现中使用如下配置:

DAO 实现之一

@Repository
public class DAOImpl implements DAOInterface {

    @Autowired
    @Qualifier("dJdbc")
    private JdbcTemplate jdbc;

    @Override
    public Map<String, Object> getBasicStudentInfo(String MAIL) {
        return jdbc.queryForMap(GET_BASIC_STUDENT_INFO, new Object[]{MAIL});
}

我应该怎样做呢?我看到很多关于多数据源的文章,但不幸的是,这些示例或解决方案并不适合我。
此外,我需要能够根据一些用户输入查询数据库。如果用户提供环境,例如“test”或“int”,我该如何根据该输入触发正确的属性?
我知道环境被@Autowired到Spring Boot中,我可以拦截用户输入,但不确定我应该如何在用户输入和DAO配置之间提供连接。
如果有什么不清楚的地方或需要更多的解释或代码,我可以提供。感谢任何帮助来解决这种情况。谢谢。
3个回答

4
以下是你问题的完整解决方案...
你的配置类将如下所示:
MySqlConfiguration.java
@Configuration
public class MySqlConfiguration {

   @Bean(name = "dMySql")
   @ConfigurationProperties(prefix = "spring.datasource.d.int-mysql")
   public DataSource mysqlDrupalDataSource() {
     return DataSourceBuilder.create().build();
   }

   @Bean(name = "dJdbc")
   public JdbcTemplate drupalJdbcTemplate(@Qualifier("dMySql") DataSource dMySql) {
      return new JdbcTemplate(dMySql);
   }

   @Bean(name = "mMySql")
   @ConfigurationProperties(prefix = "spring.datasource.m.int-mysql")
   public DataSource mysqlDrupalDataSource() {
      return DataSourceBuilder.create().build();
   }

   @Bean(name = "mJdbc")
   public JdbcTemplate drupalJdbcTemplate(@Qualifier("mMySql") DataSource mMySql) {
      return new JdbcTemplate(mMySql);
   }
}

OracleConfiguration.java

@Configuration
public class OracleConfiguration {

   @Primary
   @Bean(name = "tOracle")
   @ConfigurationProperties(prefix = "spring.datasource.test-oracle")
   public DataSource heOracleDataSource() {
      return DataSourceBuilder.create().build();
   }

   @Bean(name = "tOracleJdbc")
   public JdbcTemplate jdbcTemplate(@Qualifier("tOracle") DataSource tOracle) {
      return new JdbcTemplate(tOracle);
   }

   @Bean(name = "iOracle")
   @ConfigurationProperties(prefix = "spring.datasource.int-oracle")
   public DataSource heOracleDataSource() {
      return DataSourceBuilder.create().build();
   }

   @Bean(name = "iOracleJdbc")
   public JdbcTemplate jdbcTemplate(@Qualifier("iOracle") DataSource iOracle) {
      return new JdbcTemplate(iOracle);
   }
}

在你的DAO类中,你可以像这样自动装配JdbcTemplate:

@Repository
public class DAOImpl implements DAOInterface {

    @Autowired
    @Qualifier("dJdbc")
    private JdbcTemplate dJdbc;

    @Autowired
    @Qualifier("mJdbc")
    private JdbcTemplate mJdbc;

    @Autowired
    @Qualifier("tOracleJdbc")
    private JdbcTemplate tOracleJdbc;

    @Autowired
    @Qualifier("iOracleJdbc")
    private JdbcTemplate iOracleJdbc;

    @Override
    public Map<String, Object> getBasicStudentInfo(String MAIL) {
        return dJdbc.queryForMap(GET_BASIC_STUDENT_INFO, new Object[]{MAIL});
    }

    .
    .
    .
}
注意:确保将其中一个DataSource注释为@Primary注释

我注意到在混合使用带有JdbcTemplate和不带有JdbcTemplate的DataSources时遇到了麻烦。我发现最好按照这个例子,每个DataSource都在配置文件中定义其JdbcTemplate。 - GrandAdmiral
@Shrikant Salgar 我正在使用Spring Boot 2.0,这是我的application.properties文件的详细信息: spring.datasource-app.driver-class-name=com.microsoft.sqlserver.jdbc.SQLServerDriver spring.datasource-app.url=xxxx 但是我遇到了一个错误,提示需要jdbcUrl和driverClassName。 - Vikas Kalapur
@VikasKalapur Spring 2.0 默认使用 HikariCP 数据源,并期望 jdbc-url 配置参数名称。因此,请将您的配置更改为 spring.datasource-app.jdbc-url=xxxx 并尝试。 - Shrikant Salgar

1

我的设置:spring-boot版本1.2.5.RELEASE

我成功地运行了这样的设置,通过在每个JDBC方法创建中添加@Qualifier,正确创建了DataSources。

因此,对于每个JDBC方法,您应该像这样匹配限定数据源。

@Bean(name = "dJdbc")
public JdbcTemplate drupalJdbcTemplate(@Qualifier("dMySql") DataSource dMySql) {
    return new JdbcTemplate(dMySql);
}

无论您选择@Primary,对于每个JDBC使用@Qualifier应该都能很好地工作。在存储库中自动装配jdbcTemplates,并对它们使用@Qualifier也可以。

0
在你的DAO中,你可以连接额外的JdbcTemplate。然后在运行时,你可以选择使用哪一个。
@Repository
public class DAOImpl implements DAOInterface {

@Autowired
@Qualifier("tOracle")
private JdbcTemplate testJdbc;

@Autowired
@Qualifier("intOracle")
private JdbcTemplate intJdbc;

@Override
public Map<String, Object> getBasicStudentInfo(String MAIL, String source) {
    if ("TEST".equals(source)){
          return testJdbc.queryForMap(GET_BASIC_STUDENT_INFO, new Object[]{MAIL});
    }else {
          return intJdbc.queryForMap(GET_BASIC_STUDENT_INFO, new Object[]{MAIL});       
    }
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接