首頁 > 軟體

SpringBoot 組態檔給實體注入值方式

2022-02-17 19:01:09

組態檔給實體注入值

SpringBoot 預設的全域性組態檔有兩個 application.properties 和application.yml

properties用法

# 例如修改埠號 直接賦值
server.port=8888

yaml用法

# 例如修改埠號
server:
    port: 8888
  • YML中賦值是以鍵值對的形式,且利用縮排表示層級關係,同一級縮排必須一致
  • 大小寫敏感,支援鬆散寫法,且冒號後面必須有一個空格

通過組態檔給實體類注入屬性

// 實體類
@Component // 把實體類放入到spring容器中
@ConfigurationProperties(prefix = "student") // 識別組態檔
public class Student {
    private String name;
    private int age;
    private boolean sex;
    private Date birthday;
    private Map<String, Object> location;
    private String[] hobbies;
    private List<String> skills;
    private Pet pet;
    
    // .... set/get/toString
}
# yml 組態檔
student: 
	name: zs
	age: 23
	sex: true
	birthday: 2020/10/1
	location: {province: 湖北,city: 武漢, zone: 洪山}
	hobbies: [足球, 籃球]
	skills: [程式設計, 金融]
	pet: 
		nickName: wc
		strain: hsq

在這裡注意不同資料型別的寫法,簡單的資料直接賦值

# map型別和物件型別 的兩種寫法
# 1.行內寫法
location: {province: 湖北,city: 武漢, zone: 洪山}
pet: {nickName: wc, strain: hsq}
# 2.分行寫
location:
	province: 湖北
	city: 武漢
	zone: 洪山
pet: 
	nickName: wc
	strain: hsq
# 陣列、list、set
# 1、行內寫法, 其中中括號還可以省略
hobbies: [足球, 籃球]
skills: [程式設計, 金融]
# 2、分行寫
hobbies:
	- 足球
	- 籃球
skills: 
	- 程式設計
	- 金融

到 SpringBoot 測試檔案中測試輸出

    @Autowired
    Student student;
    @Test
    void contextLoads() {
        System.out.println(student);
    }

結果

Student{name='zs', age=23, sex=true, birthday=Thu Oct 01 00:00:00 CST 2020, location={province=湖北, city=武漢, zone=洪山}, hobbies=[足球,籃球], skills=[程式設計, 金融], pet=Pet{nickName='wc', strain='hsq'}}

上面yml中注意

# 如果對字串加單引號,雙引號會有什麼區別
location: {province: "湖北",city: '武漢', zone: 洪山}
# 如果引號中只是字串時沒什麼區別
location: {province: "湖n北",city: '武n漢', zone: 洪n山}
# 此時雙引號中的跳脫字元會被識別,會換行,單引號和不加引號會原樣輸出

也可以使用properties注入

student.name=ls
student.age=24
...

其中properties檔案和yml檔案中的值可以互相參照。兩個組態檔可以互補,properties檔案優先順序高於yml

另外如果要注入的值不在這兩個預設組態檔中,這是需要使用@PropertySource註解,遺憾的是該註解只支援properties檔案,不支援yml檔案

@PropertySource(value = {"classpath:conf.properties"})
public class Student {
    ...

組態檔值注入方式

1.1 從全域性組態檔中讀取設定到實體類 (@ConfigurationProperties)

組態檔 (application.yml)(寫在application.properties也可以,格式變一下即可)

person:
  lastName: Mary
  age: 16
  birthDate: 2004/01/01
  maps: {one:1,two:2,three:3}
  lists:
    - 1
    - 2
    - 3
  pet:
    name: wangcai
    age: 3

實體類(javaBean):

/**
 * 將組態檔中設定的每一個屬性的值,對映到這個元件中
 *
 * @Component:
 *     只有這個元件是容器中的元件,才能容器提供的@ConfigurationProperties功能;
 *
 * @ConfigurationProperties:
 *     告訴SpringBoot將本類中的所有屬性和組態檔中相關的設定進行繫結(預設組態檔為application.properties與      
 *     application.yml);
 *
 * prefix = "person":
 *       組態檔中哪個下面的所有屬性進行一一對映
 */
@Component
@ConfigurationProperties(prefix = "person")
public class Person {
    private String lastName;
    private Integer age;
    private Date birthDate;
    private Map<String,Object> maps;
    private List<Object> lists;
    private Pet pet;
    //省略get,set方法
    @Override
    public String toString() {
        String mapValue = "";
        
        if(this.maps!=null){
            for(String key:this.maps.keySet()){
                Object value = this.maps.get(key);
                mapValue += key+"t"+value+"t";
            }
        }
        return "lastName:"+this.lastName+
                "nage:"+this.age+
                "nbirthDate:"+this.birthDate+
                "nmaps:"+mapValue+
                "nlists:"+this.lists+
                this.pet;
    }
}
public class Pet {
    private String name;
    private Integer age;
    //省略get,set方法
    
    @Override
    public String toString() {
        return "nPet:ntPet name:"+this.name+
                "ntPet age:"+this.age+"n";
    }
}

我們可以匯入組態檔處理器,以後編寫設定就有提示了(pom.xml)

<!--匯入組態檔處理器,組態檔進行繫結就會有提示-->
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-configuration-processor</artifactId>
    <optional>true</optional>
</dependency>

測試

@SpringBootTest
class DemoApplicationTests {
    @Autowired
    Person person;
    @Test
    void contextLoads() {
        System.out.println(person.toString());
    }
}

1.2 全域性組態檔注入值(@Value)

@Value 其實是Spring中的註解,其功能使用xml檔案描述是這樣的:

 <bean class="Person">
     <property name="lastName" value="字面量/${key}從環境變數、組態檔中獲取值/#{SpEL}"></property>
 <bean/>

其中property表示的是Person類中的各項屬性,name用於指定具體屬性,value用於指定值。

value的值主要有3種:

  • 字面量,也就是數位(1,2…)、字串(abc)、布林變數(true、false)等常數
  • ${key},從環境變數、組態檔中獲取值
  • #{SpEL}, Spring的表示式語言,可以執行一些計算,呼叫一些函數
@Component
public class Person {
    @Value("${person.last-name}")  //@Value("#{'Lily'.toUpperCase()}")
    private String lastName;
    @Value("#{11*2}")
    private Integer age;
    private Date birthDate;
    private Map<String,Object> maps;
    private List<Object> lists;
    private Pet pet;    
    //省略get,set和toString    
}

1.3 從指定檔案讀取並設定實體類(@PropertySource+@ConfigurationProperties)

在 resources 目錄下建立 person.properties

person.lastName = Lily
person.age = 20
person.birthDate = 2000/01/01
person.maps.one = 1
person.maps.two = 2
person.lists = a,b,ch
person.pet.name = wangcai
person.pet.age = 3

更改 Person 類中的註解

@Component
@PropertySource(value = {"classpath:person.properties"})
@ConfigurationProperties(prefix = "person")
public class Person {
    //...省略屬性,get,set,toString
}

要注意的是,PropertySource 只支援properties檔案,不支援yml檔案讀取。

1.4 從指定檔案讀取並注入值(@PropertySource+@Value)

建立組態檔

更改註釋

@Component
@PropertySource(value = {"classpath:person.properties"})
public class Person {    
    @Value("${person.last-name}")
    private String lastName;    
    //...省略屬性,get,set,toString
}

以上為個人經驗,希望能給大家一個參考,也希望大家多多支援it145.com。


IT145.com E-mail:sddin#qq.com