Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

@ConditionalOnSingleCandidate does not match when there is a single candidate that is a scoped bean #22038

Closed
kazuki43zoo opened this issue Jun 20, 2020 · 1 comment
Assignees
Labels
type: bug A general bug
Milestone

Comments

@kazuki43zoo
Copy link
Contributor

When the DataSource is refresh scope(provided by spring-cloud), I cannot inject the JdbcTemplate to my component. Probably, JdbcTemplateConfiguration(auto-configure) not work.

  • Configuration class
  @Bean
  @RefreshScope
  DataSource dataSource(DataSourceProperties properties) {
    HikariDataSource dataSource = properties.initializeDataSourceBuilder().type(HikariDataSource.class).build();
    if (StringUtils.hasText(properties.getName())) {
      dataSource.setPoolName(properties.getName());
    }
    return dataSource;
  }
  • My component (controller)
  @RestController
  static class SettingsController {
    private final JdbcOperations operations;

    SettingsController(JdbcOperations operations) {
      this.operations = operations;
    }

    @GetMapping("/settings")
    public List<Map<String, Object>> getSettings() {
      return operations.queryForList("select * from settings order by key");
    }
  }
  • log
...
Error starting ApplicationContext. To display the conditions report re-run your application with 'debug' enabled.
2020-06-20 19:23:27.503 ERROR 35308 --- [           main] o.s.b.d.LoggingFailureAnalysisReporter   : 

***************************
APPLICATION FAILED TO START
***************************

Description:

Parameter 0 of constructor in com.example.demo.RefreshableDsDemoApplication$SettingsController required a bean of type 'org.springframework.jdbc.core.JdbcOperations' that could not be found.
...

Reproduce project

How to reproduce

Please run the RefreshableDsDemoApplicationTests.

NOTE:

When the DataSource is singleton scope, it work fine. (Please run the NonRefreshableDsDemoApplicationTests)

@spring-projects-issues spring-projects-issues added the status: waiting-for-triage An issue we've not yet triaged label Jun 20, 2020
@wilkinsona
Copy link
Member

Thanks for the sample. The problem is that using @RefreshScope results in two DataSource beans in the context, dataSource and scopedTarget.dataSource. This causes the @ConditionalOnSingleCandidate auto-configuration of JdbcTemplate to back off:

  JdbcTemplateAutoConfiguration:
      Did not match:
         - @ConditionalOnSingleCandidate (types: javax.sql.DataSource; SearchStrategy: all) did not find a primary bean from beans 'scopedTarget.dataSource', 'dataSource' (OnBeanCondition)

I think we need to ignore scoped targets when searching for a single candidate.

@wilkinsona wilkinsona added type: bug A general bug and removed status: waiting-for-triage An issue we've not yet triaged labels Jun 20, 2020
@wilkinsona wilkinsona added this to the 2.2.x milestone Jun 20, 2020
@wilkinsona wilkinsona changed the title Cannot inject JdbcTemplate when DataSource is refresh scope @ConditionalOnSingleCandidate does not match when there is a single candidate that is a scoped bean Jul 2, 2020
@wilkinsona wilkinsona self-assigned this Jul 2, 2020
@wilkinsona wilkinsona modified the milestones: 2.2.x, 2.2.9 Jul 2, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
type: bug A general bug
Projects
None yet
Development

No branches or pull requests

3 participants