Spring Boot 自動裝配


@Configuration和@Bean

Spring提供了注解@Configuration和@Bean注解用來配置多個Bean,在以前的Spring項目中可以通過xml的方式配置:

<beans>
  <bean id=”xxxBean” class="aaa.bbb.xxxBean"></bean>
</beans>

采用Configuration注解的方式如下:

//@SpringBootConfiguration
@Configuration
public class TestConfiguration {

    @Bean
    public  EncodingConvert createUTF8EncodingConvert(){
        return  new UTF8EncodingConvert();
    }

    @Bean
    public  EncodingConvert createGBKEncodingConvert(){
        return  new GBKEncodingConvert();
    }
}

上面代碼中TestConfiguration類使用注解@ Configuration,向Spring表明這是一個配置類,類里的含有@Bean注解的方法都會被Spring調用,返回對象將會為Spring容器管理的Bean,注解@Bean可以給Bean指定一個名稱,如@Bean(“xxxBean”),如不指定,則將會以該方法名作為Bean的名稱

條件裝配

Spting Boot提供一系列@ConditionalOnXXX的注解用於不同場景下的Bean裝配。基本上通過注解名稱就能明白用途,@ConditionalOnXXX注解可以作用於類或者方法上。

1.作用用於類上,需要和 @Configuration注解一起使用,決定該配置類是否生效

2.作用於方法上,需要和@Bean注解一起使用,判斷該@Bean是否生成

Bean條件裝配

Spring Boot可以通過有沒有指定Bean來決定是否配置當前Bean,

使用@ConditionalOnBean,在當前上下文中存在某個對象時,才會實例化當前Bean;

使用@ConditionalOnMissingBean,在當前上下文中不存在某個對象時,才會實例化當前Bean。

@Configuration
@ConditionalOnBean(PropertiesConfig.class)
public class TestConfiguration {

    @Bean
    @ConditionalOnMissingBean
    public  EncodingConvert createUTF8EncodingConvert(){
        return  new UTF8EncodingConvert();
    }

    @Bean
    public  EncodingConvert createGBKEncodingConvert(){
        return  new GBKEncodingConvert();
    }
}

TestConfiguration配置生效的前提是當前上下文中已經配置了PropertiesConfig。

如果當前上下文中沒有UTF8EncodingConvert類型Bean,則調用createUTF8EncodingConvert創建。

Class條件裝配

Class條件裝配是按照某個類是否在Classpath中來判斷是否需要配置Bean。

@ConditionalOnClass:表示classpath有指定的類時,配置才生效

@ConditionalOnMissingClass:表示當classpath中沒有指定類,則配置生效

@Configuration
@ConditionalOnClass(JestClient.class)
//@ConditionalOnClass(name="com.sl.springbootdemo.JestClient")
public  class JestAutoConfiguration{

}

Environment裝配

Spring Boot可以根據Environment屬性來決定是否實例化Bean,通過@ConditionalOnProperty注解來實現。根據注解屬性name讀取Spring Boot的Environment的變量包含的屬性 ,再根據屬性值與注解屬性havingValue的值比較,判斷否實例化Bean,如果沒有指定注解屬性havingValue,name只要environment屬性值不為false,都會實例化Bean。MatchIfMissing=true,表示如果evironment沒有包含message.center.enavled屬性,也會實例化Bean,默認是false。

@Bean
@ConditionalOnProperty(name="com.sl.Encoding",havingValue = "GBK",matchIfMissing = false)
public  EncodingConvert createGBKEncodingConvert(){
    return  new GBKEncodingConvert();
}

其他條件裝配注解:

@ConditionalOnExpression :當表達式為true時,才會實例化一個Bean,支持SpEL表達式

@ConditionalOnNotWebApplication:表示不是web應用,才會實例化一個Bean

Condition接口(自定義條件裝配)

當Spring Boot提供的一些列@ConditionalOnXXX注解無法滿足需求時,也可以手動構造一個Condition實現,使用注解@Conditional來引用Condition實現。

Condition接口定義:

@FunctionalInterface
public interface Condition {

   /**
    * Determine if the condition matches.
    * @param context the condition context
    * @param metadata metadata of the {@link org.springframework.core.type.AnnotationMetadata class}
    * or {@link org.springframework.core.type.MethodMetadata method} being checked
    * @return {@code true} if the condition matches and the component can be registered,
    * or {@code false} to veto the annotated component's registration
    */
   boolean matches(ConditionContext context, AnnotatedTypeMetadata metadata);

}

參數ConditionContext類可以獲取用於幫助條件判斷的輔助類:

1.Environment:讀取系統屬性、環境變量、配置參數等。

2.ResourceLoader:加載判斷資源文件

3.ConfigurableListableBeanFactory:Srping容器

下面是一個實現示例,當application.properties配置文件中存在配置file.encoding=GBK時才創建Bean實例

public class GBKCondition implements Condition {
    public boolean matches(ConditionContext context, AnnotatedTypeMetadata metadata){
        String encoding = context.getEnvironment().getProperty("file.encoding");

        if("gbk".equals(encoding.toLowerCase())){
            return  true;
        }
        return  false;
     }
}

使用:

@Bean
@Conditional(GBKCondition.class) //使用自定義Condition
public  EncodingConvert createGBKEncodingConvert(){
    return  new GBKEncodingConvert();
}

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM