Spring bean依赖于条件bean

时间:2018-03-23 09:25:51

标签: java spring spring-boot

我想要一个spring bean在另一个bean 之后实现。所以我只使用@DependsOn注释。

事情是:这个其他豆是一个有条件的豆子穿着 @ConditionalOnProperty(name = "some.property", havingValue = "true")注释。 因此,当属性为false时,bean不会被实例化(这就是我们想要的),@DependsOn显然会失败。这里的目标是:无论如何创建第二个bean,但是在第一个bean 之后创建它

有没有办法在不删除@ConditionalOnProperty的情况下执行此操作?并且不使用@Order注释?

感谢您的帮助

4 个答案:

答案 0 :(得分:4)

以下方法如何:

interface Something {}

public class FirstBean implements Something {}

public class SecondBean implements Something{} // maybe empty implementation

现在配置如下:

@Configuration
public class MyConfiguration {

  @Bean(name = "hello")
  @ConditionalOnProperty(name = "some.property", havingValue = true) 
  public Something helloBean() {
     return new FirstBean();
  }

  @Bean(name = "hello")
  @ConditionalOnProperty(name = "some.property", havingValue = false) 
  public Something secondBean() {
     return new SecondBean();
  }

  @Bean
  @DependsOn("hello")
  public MyDependantBean dependantBean() {
       return new MyDependantBean();
  }
}

我的想法是创建“Something”bean(即使它是一个空的实现),这样依赖bean在任何情况下都依赖于Something。

我自己没试过,你知道,春天充满魔力,但可能值得一试:)

答案 1 :(得分:1)

您可以使用@DependsO代替使用@AutoConfigureAfter(),即使没有创建第一个bean,也可以保留第二个bean的顺序。

@Configuration
public class FirstConfiguration {

  @Bean(name = "firstBean")
  @ConditionalOnProperty(name = "some.property", havingValue = true) 
  public FirstBean firstBean() {
     return new FirstBean();
  }
}

@Configuration
@AutoConfigureAfter(name = {"firstBean"})
public class SecondConfiguration {

  @Bean
  public SecondBean secondBean() {
       return new SecondBean();
  }
}

答案 2 :(得分:0)

您可以使用自定义条件类:

public class BeanPresennceCondition implements Condition {

  @Override
  public boolean matches(ConditionContext context, AnnotatedTypeMetadata metadata) {
      FirstBean firstBean = null;
      try {
      firstBean = (FirstBean)context.getBeanFactory().getBean("firstBean"); 
      }catch(NoSuchBeanDefinitionException ex) {

      }
     return firstBean != null;
  }
}

答案 3 :(得分:0)

您能为从属bean创建两个定义,以解决另一个bean存在或不存在的两种情况吗?

例如:

@Bean(name = "myDependentBean")
@DependsOn("otherBean")
@ConditionalOnProperty(name = "some.property", havingValue = true) 
public DependentBean myDependentBean() {
    return new DependentBean();
}

@Bean(name = "myDependentBean")
@ConditionalOnProperty(name = "some.property", havingValue = false, matchIfMissing = true) 
public DependentBean myDependentBean_fallback() {
    return new DependentBean();
}

(这是我今天用来解决类似问题的方法!)

然后,如果some.propertytrue,Spring将使用第一个定义,因此在myDependentBean之后实例化otherBean。如果缺少some.propertyfalse,Spring将使用第二个定义,因此不必关心otherBean

或者,您可以在它们上使用@ConditionalOnBean / @ConditionalOnMissingBean而不是@ConditionalOnProperty(尽管我没有尝试过)。