簡體   English   中英

Spring bean 依賴於條件 bean

[英]Spring bean depends on a conditional bean

我想要一個 spring bean在另一個 bean 之后被實例化。 所以我只是使用@DependsOn注釋。

問題是:這個其他 bean 是一個@ConditionalOnProperty(name = "some.property", havingValue = "true")注釋的條件 bean。 因此,當屬性為 false 時,bean 不會被實例化(這就是我們想要的),並且@DependsOn顯然失敗了。 這里的目標是:無論如何創建第二個 bean,但如果它被創建,則在第一個 bean 之后創建它。

有沒有辦法在不刪除@ConditionalOnProperty情況下做到這@ConditionalOnProperty 並且不使用@Order注釋?

謝謝你的幫助

以下方法如何:

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。

我自己沒有嘗試過,你知道,春天充滿魔力,但可能值得一試:)

您能否為依賴 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.property丟失或為false ,Spring 將使用第二個定義,因此不關心otherBean

或者,您可以在這些上使用@ConditionalOnBean / @ConditionalOnMissingBean而不是@ConditionalOnProperty (盡管我還沒有嘗試過)。

您可以使用@AutoConfigureAfter()而不是使用@DependsO ,這將允許創建第二個 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();
  }
}

您可以使用自定義條件類:

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;
  }
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM