1. 程式人生 > >springboot 外部配置<中篇> YAML文件代替屬性文件

springboot 外部配置<中篇> YAML文件代替屬性文件

set onf another ade list() factory oot 生產 環境

YAML是JSON格式的擴展集,是一種非常方便的用來定義屬性的文件格式。當你的項目有SnakeYAML庫時,Spring Boot將會自動支持它。

1、使用YAML文件

SpringFramework中有兩個類可以加載YAML文件,YamlPropertiesFactoryBean 可以加載之為屬性類PropertiesYamlMapFactoryBean 可以加載之為Map。

加載YAML文件

如下YAML文件

environments:
    dev:
        url: http://dev.bar.com
        name: Developer Setup
    prod:
        url: http:
//foo.bar.com name: My Cool App

轉化為屬性文件為

environments.dev.url=http://dev.bar.com
environments.dev.name=Developer Setup
environments.prod.url=http://foo.bar.com
environments.prod.name=My Cool App

YAML列表將會轉化為帶[index]字符串的Key,如

my:
   servers:
       - dev.bar.com
       - foo.bar.com

將被轉換為

my.servers[0]=dev.bar.com
my.servers[
1]=foo.bar.com

想要想Spring DataBinder工具(這裏用的是@ConfigurationProperties註解)那樣綁定對象到實體Bean中的List或Set屬性上的話,你不需要為改屬性提供setter或者初始化該屬性,只需要如下就行

@ConfigurationProperties(prefix="my")
public class Config {

    private List<String> servers = new ArrayList<String>();

    public List<String> getServers() {
        
return this.servers; } }

2、暴露YAML文件至Spring Environment

通常用YamlPropertySourceLoader來將YAML文件作為屬性資源文件暴露給Spring Environment。這能讓你通過使用@Value註釋+占位符語法來訪問這些環境變量。

3、多重配置 YAML 文檔。

你可以在單個文件夾裏面配置多個重復的YAML 文檔並通過spring.profiles的值來表明你想用哪一個,例如:

server:
    address: 192.168.1.100
---
spring:
    profiles: development
server:
    address: 127.0.0.1
---
spring:
    profiles: production
server:
    address: 192.168.1.120

在上面例子中,開發環境中的服務器地址將是127.0.0.1,生產環境的服務器地址則為192.168.1.100,如果spring的profiles為不可用狀態,則為192.168.1.100。

在沒有指定的情況下profiles通常是激活的。所以在這個文件中我們設一個僅僅對"default" profiles有效的security.user.password。

server:
  port: 8000
---
spring:
  profiles: default
security:
  user:
    password: weak

而在下面的例子中,密碼總是被設置因為它沒有被綁定到任何profiles,因此它會在所有其他的profiles裏面也都被重置。

4、YAML缺點

YAML文件不能通過@PropertySource註解進行加載。

5、YAML列表的合並

從上面我們可以看到,YAML最終被轉換成Properties。當通過profiles來覆蓋一個list屬性時候,程序將變成一個計數器往list添加數據。

例如,假設類MyPojo包含兩個默認為null的屬性name和discretion,讓我們通過FooProperties類來對他們進行暴露。

@ConfigurationProperties("foo")
public class FooProperties {

    private final List<MyPojo> list = new ArrayList<>();

    public List<MyPojo> getList() {
        return this.list;
    }

}

想一下如下配置

foo:
  list:
    - name: my name
      description: my description
---
spring:
  profiles: dev
foo:
  list:
    - name: my another name

如果dev為激活狀態,FooProperties.list只包含一個entry即上面定義的。如果dev為激活狀態,也僅僅包含下面定義的entry。它並不會合並。

springboot 外部配置<中篇> YAML文件代替屬性文件