覆盖默认数据源getConnection()

时间:2017-07-07 21:49:55

标签: spring-boot

我正在尝试将Spring应用程序(大部分)转换为Spring Boot应用程序。在应用程序中,我有一个HTTP基本过滤器,用于收集用户名和密码,然后将其作为变量传递到DataSource实现中。

在这个DataSource中,getConnection()方法是这样的:

@Override\n public Connection getConnection() throws SQLException {
Statement  stmt = null;

try {
    ConnectionWrapper connection = this.authenticatedConnection.get();
    if (connection == null) {
        connection = new ConnectionWrapper(this.dataSource.getConnection());

        StringBuilder command;

        // The CONNECT command allows indicating a user name, a password
        // and a database to initiate a
        // new session in the server with a new profile.
        command = new StringBuilder("CONNECT USER ").append(this.parameters.get().get(USER_NAME)).append(" PASSWORD ")
                .append("'").append(this.parameters.get().get(PASSWORD_NAME)).append("'").append(" DATABASE ")
                .append(this.parameters.get().get(DATA_BASE_NAME));

        this.authenticatedConnection.set(connection);

        stmt = connection.createStatement();
        stmt.execute(command.toString());
    }

    return connection;
} catch (final SQLException e) {...`

(由于StackOverflow格式问题,\ n作为新行)

在Spring中,我能够毫无问题地实现@Autowired Private DataSource dataSource。在Spring Boot中,据我所知,Object需要是一个使用@Autowired的Bean,但是当我在这个实现的DataSource之前添加@Bean时,我得到“不允许注释@Bean这个位置”

我怎样才能得到它以便我可以做一个dataSource.getConnection();并从主DataSource获取连接,或者能够覆盖主DataSource的方法?

我看到它的方式,按优先顺序列出了4种可能的解决方案:

  1. 创建一个实际覆盖spring.datasource'方法的数据源。
  2. 将此实现“Beanified”,这样我就可以再次@Autowired dataSource。
  3. 我想我可以跳过@Autowired,只需设置this.dataSource = [对application.properties中定义的spring.datasource的未知引用]
  4. 创建另一个使用spring.datasource属性配置的DataSource类ProgrammedDataSource,然后将其设置为this.dataSource = new ProgrammedDataSource();
  5. 但我实施这些解决方案的尝试产生了这个问题。

1 个答案:

答案 0 :(得分:0)

我明白了。我不需要在那里制作Bean,虽然我仍然不确定为什么我不允许在DataSource之前调用@Bean,但不管怎样。

在我的应用程序中:

public class ServiceApplication {

@Bean
@Primary
@ConfigurationProperties("spring.datasource")
 public DataSource dataSource(){
  return DataSourceBuilder.create().build();
 }

@Bean(name="AuthDataSource")
public DataSource authDataSource() {
        return new AuthDataSource();
}

public static void main(String[] args) {
    SpringApplication.run(ServiceApplication.class, args);
}

}

在控制器中我有:

@Controller
@RequestMapping("/service")
public class ServiceController {

      @Autowired
      public void MyBean(JdbcTemplate jdbcTemplate) {
        this.jdbcTemplate = new JdbcTemplate(new AuthDataSource());
      } ...

但是,因为我在JdbcTemplate中调用了新的AuthDataSource(),所以它没有进行自动装配。现在控制器看起来像这样,它可以工作:

@Controller
@RequestMapping("/service")
public class ServiceController {

      @Autowired
      @Qualifier("AuthDataSource")
      private DataSource datasource;
      private JdbcTemplate jdbcTemplate;

      @Autowired
      public void MyBean(JdbcTemplate jdbcTemplate) {
        this.jdbcTemplate = new JdbcTemplate(this.dataSource);
      } ...