Version: Next

yaml语法

SpringBoot配置文件所有配置内容

删除application.properties,新建application.yaml

配置文件

SpringBoot使用一个全局的配置文件,配置文件名称是固定的

  • application.properties

    • 语法结构

      key=value
  • application.yaml

    • 语法结构

      key:空格value

yaml概述

yaml是"YAML Ain't a Markup language" (YAML不是一种标记语言)的递归缩写。在开发这种语言时,YAML的意思是"Yet Another Markup Language"(还是一种标记语言)

这种语言以数据作为中心,而不是以标记语言为重点

  • 传统xml配置

    <server>
    <prot>8080</prot>
    </server>
  • yaml配置

    server:
    port: 8080

yaml基础语法

语法要求严格

  1. 空格不能省略
  2. 以缩进来控制层级关系,只要是左边对齐的一列数据都是同一个层级
  3. 属性和值的大小写都是十分敏感的

字面量:普通值的[数字,布尔值,字符串]

key: value
  • 双引号"":不会转义特殊字符 name: "Alice \n Taylor" -> Alice 换行 Taylor
  • 单引号'':会转义特殊字符为普通字符 name: 'Alice \n Taylor' -> Alice \n Taylor

对象、Map键值对

#对象,Map键值对
key:
value1:
value2:

student对象

student:
name: Alice
age: 3

行内写法

student: {name: Alice, age: 3}

数组(List、Set)

pets:
- cat
- dog
- pig

行内写法

pets: [cat, dog, pig]

应用:修改SpringBoot默认端口

server:
port: 9000

注入配置文件

yaml可以直接给实体类赋值

  • pojo

    @Component
    public class Cat {
    private String name;
    private Integer age;
    public String getName() {
    return name;
    }
    public void setName(String name) {
    this.name = name;
    }
    public Integer getAge() {
    return age;
    }
    public void setAge(Integer age) {
    this.age = age;
    }
    public Cat() {
    }
    public Cat(String name, Integer age) {
    this.name = name;
    this.age = age;
    }
    }
    @Component
    public class Person {
    private String name;
    private Integer age;
    private Boolean happy;
    private Date birthday;
    private Map<String, Object> maps;
    private List<Object> list;
    private Cat cat;
    public Person(String name, Integer age, Boolean happy, Date birthday, Map<String, Object> maps, List<Object> list, Cat cat) {
    this.name = name;
    this.age = age;
    this.happy = happy;
    this.birthday = birthday;
    this.maps = maps;
    this.list = list;
    this.cat = cat;
    }
    public Person() {
    }
    public String getName() {
    return name;
    }
    public void setName(String name) {
    this.name = name;
    }
    public Integer getAge() {
    return age;
    }
    public void setAge(Integer age) {
    this.age = age;
    }
    public Boolean getHappy() {
    return happy;
    }
    public void setHappy(Boolean happy) {
    this.happy = happy;
    }
    public Date getBirthday() {
    return birthday;
    }
    public void setBirthday(Date birthday) {
    this.birthday = birthday;
    }
    public Map<String, Object> getMaps() {
    return maps;
    }
    public void setMaps(Map<String, Object> maps) {
    this.maps = maps;
    }
    public List<Object> getList() {
    return list;
    }
    public void setList(List<Object> list) {
    this.list = list;
    }
    public Cat getCat() {
    return cat;
    }
    public void setCat(Cat cat) {
    this.cat = cat;
    }
    }

yaml注入

person:
name: Alice
age: 3
happy: false
birthday: 2020/04/25
maps: {k1: v1, k2: v2}
list:
- code
- music
- girl
cat:
name: miaomiao
age: 3

@configurationProperties

用来将类与yaml文件中的字段绑定

@Component
@ConfigurationProperties(prefix = "person")
public class Person {
private String name;
private Integer age;
private Boolean happy;
private Date birthday;
private Map<String, Object> maps;
private List<Object> list;
private Cat cat;
//...

使用这个注解会出现爆红,官方推荐我们导入这个maven坐标,但是不导入也是可以用的

<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-configuration-processor</artifactId>
<optional>true</optional>
</dependency>
  • 测试

    重写以下实体类的toString方法

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

    注入成功

    Person{name='Alice', age=3, happy=false, birthday=Sat Apr 25 00:00:00 CST 2020, maps={k1=v1, k2=v2}, list=[code, music, girl], cat=Cat{name='miaomiao', age=3}}

占位符

还可以在yaml文件中插入一些随机内容

  • 随机生成uuid
  • 随机生成整型数
  • 读取person的hello属性
    • 如果hello属性不存在,则默认值为hello,拼上_旺财,最终值为hello_旺财
    • 如果hello属性存在,则读取hello属性的值,再拼上_旺财
person:
name: Alice${random.uuid}
age: ${random.int}
happy: false
birthday: 2020/04/25
maps: {k1: v1, k2: v2}
list:
- code
- music
- girl
cat:
name: ${person.hello: hello}_旺财
age: 3
Person{name='Aliced2a548a2-3de1-49e2-84db-263c4bb75d86', age=1137300524, happy=false, birthday=Sat Apr 25 00:00:00 CST 2020, maps={k1=v1, k2=v2}, list=[code, music, girl], cat=Cat{name='hello_旺财', age=3}}

@PropertySource

加载指定配置文件

@Component
@PropertySource("classpath:xxx.properties")
public class Person {
@Value("$(name)")
private String name;
private Integer age;
private Boolean happy;
private Date birthday;
private Map<String, Object> maps;
private List<Object> list;
private Cat cat;
//...

这种方式只能用@Value赋值,但是还可以用EL表达式来取值

yaml和property对比

@ConfigurationProperties(yaml)@PropertySource + @Value(properties)
功能批量注入配置文件中的属性一个个指定
松散绑定支持不支持
SpEL不支持支持
JSR303校验支持不支持
复杂类型封装支持不支持
  • 松散绑定:user_nameuserName可以产生映射
  • 复杂类型封装:yaml中可以直接封装对象