SpringBoot入門(五)——自定義配置

本文來自網易雲社區html


大部分比薩店也提供某種形式的自動配置。你能夠點葷比薩、素比薩、香辣意大利比薩,或者是自動配置比薩中的極品——至尊比薩。在下單時,你並無指定具體的輔料,你所點的比薩種類決定了所用的輔料。但若是你想要至尊比薩上的所有輔料,還想要加墨西哥胡椒,又不想放蘑菇該怎麼辦?你偏心辣食又不喜歡吃菌類,自動配置不適合你的口味,你就只能本身配置比薩了嗎?固然不是,大部分比薩店會讓你以菜單上已有的選項爲基礎進行定製。java


   

外化屬性

屬性源

爲了使應用能適應不一樣的環境,SpringBoot支持外化配置。可使用.properties文件、YAML文件、環境變量、命令行參數等方式。spring

SpringBoot能從多種屬性源得到屬性,包括如下幾處:apache

  1. 命令行參數json

  2. JVM系統屬性安全

  3. 操做系統環境變量app

  4. 隨機生成的帶random.*前綴的屬性(在設置其餘屬性時,能夠引用它們,好比${random.long})dom

  5. 應用程序之外的application.properties或者application.yml文件spring-boot

  6. 打包在應用程序內的application.properites或者application.yml文件ui

  7. 經過@propertySource標註的屬性源

  8. 默認屬性


優先級由高到低,即在上面的列表中「命令行參數」的優先級最高,會覆蓋下面其餘屬性源的相同配置。

這裏只挑選了部分比較常見的屬性源,詳細信息能夠參考官網教程:24. Externalized Configuration

默認狀況下SpringApplication將任何可選的命令行參數(以'--'開頭,好比,--server.port=9000)轉化爲property,並將其添加到Spring Environment中。如上所述,命令行屬性老是優先於其餘屬性源。

若是不想用這個特性能夠用SpringApplication.setAddCommandLineProperties(false)來禁用。


YAML

SpringBoot支持YAML格式的配置文件文件後綴爲yml,是一種更易讀寫的通用的數據串行化格式。

在SpringBoot中.yml效果至關於.properties,一般狀況下兩者是能夠互相替換的,好比下面2種配置文件在SpringBoot中是等效的:

application.properties

server.port=8020
server.address=127.0.0.1

application.yml

server:  port: 8020  address: 127.0.0.1

.yml文件在配置數據的時候具備面向對象的特性,更易閱讀。

雖然.yml配置和.properties基本等效,但也有略微區別,.yml配置不能用@propertySource註解加載。  


Application屬性文件

SpringBoot會從如下位置加載.properties或.yml配置文件:

  1. 當前目錄下的/config目錄

  2. 當前目錄

  3. classpath下的/config目錄

  4. classpath的根目錄


優先級也是從高到低,高優先級的配置文件會覆蓋低優先級的配置。

使用.properties或.yml配置文件能夠對SpringBoot的自動配置進行覆蓋,好比在默認的狀況下http端口爲8080,咱們能夠像上面的例子那樣在修改成8020。

SpringBoot提供了上百個這樣能夠覆蓋的配置,具體能夠查閱官網或者查看autoconfiguration包的的META-INF/spring-configuration-metadata.json和META-INF/additional-spring-configuration-metadata.json文件(這2個文件用來給IDE作輸入提示用,有一些簡單的描述)。


類型安全的配置屬性

有時候使用@Value("#{property}")註解注入配置會比較笨重,SpringBoot提供一個類型安全的方案,用強類型的Bean對象來替代屬性。

@ConfigurationProperties用法以下

@ConfigurationProperties(prefix = "acme")public class AcmeProperties {    private boolean enabled;    private final Security security = new Security();    // 省略getter、setter

    public static class Security {        private String username;        private String password;        private List<String> roles = new ArrayList<>(Collections.singleton("USER"));        // 省略getter、setter
    }
}

@ConfigurationProperties的參數prefix表示前綴,AcmeProperties裏的每一個屬性的名稱即是具體的配置名。好比成員變量enabled綁定屬性acme.enabled。

上面這個例子表示AcmeProperties對象分別綁定下列屬性:

  • acme.ebalbe:布爾類型

  • acme.security.username:String類型

  • acme.security.pasword:String類型

  • acme.security.roles:類型是一個String集合


綁定配置以後還須要註冊Spring上下文中,有3種方式:


  1. 在java配置類中用@EnableConfigurationProperties註解激活

@Configuration@EnableConfigurationProperties(AcmeProperties.class)public class MyConfiguration {
}
  1. 直接在AcmeProperties加@Component註解


@Component@ConfigurationProperties(prefix="acme")public class AcmeProperties {    // ... see the preceding example}
  1. 在配置類中與@Bean註解組合


@Beanpublic AnotherComponent anotherComponent() {
    ...
}

註冊以後,能夠在任意地方使用@Autowire註解注入使用。


鬆散的綁定(Relaxed binding)

Spring Boot使用一些寬鬆的規則用於綁定Environment屬性到@ConfigurationProperties beans,因此Environment屬性名和bean屬性名不須要精確匹配。常見的有虛線匹配大寫(好比,context-path綁定到contextPath)和將環境屬性轉爲大寫字母(好比,PORT綁定port)。

好比:

@ConfigurationProperties(prefix="acme.my-project.person")public class OwnerProperties {    private String firstName;    // 省略getter、setter}

能夠綁定到:

Property Note
acme.my-project.person.firstName 標準的駝峯式命名
acme.my-project.person.first-name 虛線表示,適用於.properties和.yml
acme.my-project.person.first_name 下劃線表示,適用於.properties和.yml
ACME_MYPROJECT_PERSON_FIRSTNAME 大寫形式,適用於環境變量


@ConfigurationProperties vs @Value

Feature @ConfigurationProperties @Value
Relaxed binding Yes No
Meta-data support Yes No
SpEL evaluation No Yes


其餘

查看當前生效的配置

SpringBoot默認提供了大量的自動配置,咱們能夠經過啓動時添加--debug參數來查看當前的配置信息。

激活的配置以下:

Positive matches:-----------------   CodecsAutoConfiguration matched:
      - @ConditionalOnClass found required class 'org.springframework.http.codec.CodecConfigurer'; @ConditionalOnMissingClass did not find unwanted class (OnClassCondition)

   CodecsAutoConfiguration.JacksonCodecConfiguration matched:
      - @ConditionalOnClass found required class 'com.fasterxml.jackson.databind.ObjectMapper'; @ConditionalOnMissingClass did not find unwanted class (OnClassCondition)...

未激活的配置以下:

Negative matches:-----------------
   ActiveMQAutoConfiguration:
      Did not match:
         - @ConditionalOnClass did not find required classes 'javax.jms.ConnectionFactory', 'org.apache.activemq.ActiveMQConnectionFactory' (OnClassCondition)
   AopAutoConfiguration:
      Did not match:
         - @ConditionalOnClass did not find required classes 'org.aspectj.lang.annotation.Aspect', 'org.aspectj.lang.reflect.Advice', 'org.aspectj.weaver.AnnotatedElement' (OnClassCondition)
...

能夠清楚的看到每一個配置的條件,未激活的配置能夠從這裏直觀的看到緣由。

debug能夠用-Ddebug或--debug來啓用,也能夠在.properties或.yml文件中配置debug的值爲true。  


去除指定的自動配置

用@EnableAutoConfiguration註解的exclude參數去除指定的自動配置:

import org.springframework.boot.autoconfigure.*;import org.springframework.boot.autoconfigure.jdbc.*;import org.springframework.context.annotation.*;@Configuration@EnableAutoConfiguration(exclude={DataSourceAutoConfiguration.class})public class MyConfiguration {
}


小結

本節介紹了SpringBoot自定義配置的幾種方式。經過屬性外化,咱們能夠靈活選擇不一樣的屬性元來應對不一樣的場景。利用YAML可讓配置文件結構化更易於閱讀,特別是有多層結構的屬性。@ConfigurationProperties提供類型安全的屬性使用方式,使用起來更加直觀。組合使用YAML和@ConfigurationProperties相信能讓項目的配置變得更加清晰。

SpringBoot不只僅是幫助咱們快速搭建一個可用的項目,在使用便利性上也提供了更多的姿式。


 


相關閱讀:SpringBoot入門(一)——開箱即用

SpringBoot入門(二)——起步依賴

SpringBoot入門(三)——入口類解析

SpringBoot入門(四)——自動配置

SpringBoot入門(五)——自定義配置

       

網易雲新用戶大禮包:https://www.163yun.com/gift

 

本文來自網易實踐者社區,經做者金港生受權發佈。

相關文章
相關標籤/搜索