在实际开发中,我们会遇到关于配置文件的读取,获取配置文件的自定义配置,以及如何多环境下的配置文件信息的获取。
配置读取优先级
命令行参数。
从
java:comp/env
得到的 JNDI 属性。通过
System.getProperties()
获取的 Java 系统参数。操作系统环境变量。
RandomValuePropertySource
配置的random.*
属性值。如 ${random.int}、${random.long}、${random.value}、${random.uuid} 等。JAR 包外部的
application-{profile}.properties
或application.yml
(带 spring.profile)配置文件。JAR 包内部的
application-{profile}.properties
或application.yml
(带 spring.profile)配置文件。JAR 包外部的
application.properties
或application.yml
(不带 spring.profile)配置文件。JAR 包内部的
application.properties
或application.yml
(不带 spring.profile)配置文件。
(从 JAR 包外向 JAR 包内进行寻找,优先加载带{profile}
的文件,再加载不带{profile}
的文件)@Configuration
注解类上的@PropertySource
。通过
SpringApplication.setDefaultProperties
指定默认属性。
注意:application.properties
文件的优先级高于 application.yml
文件的优先级。
配置依赖项
在 pom.xml 文件中,加入 spring-boot-configuration-processor
依赖项,用于读取配置值。
1 | <dependency> |
2 | <groupId>org.springframework.boot</groupId> |
3 | <artifactId>spring-boot-configuration-processor</artifactId> |
4 | <optional>true</optional> |
5 | </dependency> |
属性配置与实体类的映射
- application.properties
1 | # 32 位随机字符串 |
2 | ${random.value} = |
3 | # 随机的 int 类型数字 |
4 | ${random.int} = |
5 | # 随机的 long 类型数字 |
6 | ${random.long} = |
7 | # 100 以内的随机int类型 |
8 | ${random.int(100)} = |
9 | # 0-100 范围内的随机int类型 |
10 | ${random.int[0,100]} = |
- author.properties
1 | yifanzheng = |
2 | star = |
3 | good boy! = |
方式一
在 @Configuration
注解的类上加上 @ConfigurationProperties(prefix="前缀名")
注解,可以使用 @PropertySource
注解指定加载的配置文件,不加时默认加载 application.properties
文件
1 | /** |
2 | * AuthorConfig |
3 | * |
4 | * @author star |
5 | **/ |
6 |
|
7 | "author") (prefix = |
8 | "classpath:author.properties") // 指定配置文件的位置 (value = |
9 | public class AuthorConfig { |
10 | |
11 | private String name; |
12 | |
13 | private String nickname; |
14 | |
15 | private String intro; |
16 | |
17 | public String getName() { |
18 | return name; |
19 | } |
20 | |
21 | public void setName(String name) { |
22 | this.name = name; |
23 | } |
24 | |
25 | public String getNickname() { |
26 | return nickname; |
27 | } |
28 | |
29 | public void setNickname(String nickname) { |
30 | this.nickname = nickname; |
31 | } |
32 | } |
注意:使用这种方式配置的类,在使用 @Autowired 注入时,不能直接 return 注入的对象,它只是指向 Spring 容器中对象资源的一个标识,可以通过这个标识返回该对象中的值。
方式二
使用 @Value
注解,直接映射实体类的各个属性。
1 | /* |
2 | * RandomConfig |
3 | * |
4 | * @author star |
5 | **/ |
6 |
|
7 | public class RandomConfig { |
8 | |
9 | "${rand.stringValue}") ( |
10 | private String stringValue; |
11 | |
12 | "${rand.intNumber}") ( |
13 | private Integer intNumber; |
14 | |
15 | "${rand.longNumber}") ( |
16 | private Long longNumber; |
17 | |
18 | "${rand.number}") ( |
19 | private Integer number; |
20 | |
21 | "${rand.rangeNumber}") ( |
22 | private Integer rangeNumber; |
23 | |
24 | public String getStringValue() { |
25 | return stringValue; |
26 | } |
27 | |
28 | public void setStringValue(String stringValue) { |
29 | this.stringValue = stringValue; |
30 | } |
31 | |
32 | public Integer getIntNumber() { |
33 | return intNumber; |
34 | } |
35 | |
36 | public void setIntNumber(Integer intNumber) { |
37 | this.intNumber = intNumber; |
38 | } |
39 | |
40 | public Long getLongNumber() { |
41 | return longNumber; |
42 | } |
43 | |
44 | public void setLongNumber(Long longNumber) { |
45 | this.longNumber = longNumber; |
46 | } |
47 | |
48 | public Integer getNumber() { |
49 | return number; |
50 | } |
51 | |
52 | public void setNumber(Integer number) { |
53 | this.number = number; |
54 | } |
55 | |
56 | public Integer getRangeNumber() { |
57 | return rangeNumber; |
58 | } |
59 | |
60 | public void setRangeNumber(Integer rangeNumber) { |
61 | this.rangeNumber = rangeNumber; |
62 | } |
63 | } |
方式三
在方法上使用 @Bean
注解,配合以上注解使用。
1 | /** |
2 | * AuthorBeanConfig 使用 @Bean 注解的方式获取配置信息 |
3 | * |
4 | * @author star |
5 | **/ |
6 |
|
7 | "classpath:author.properties") (value = |
8 | public class AuthorBeanConfig { |
9 | |
10 | |
11 | "author") (prefix = |
12 | public AuthorBean getAuthorBean(){ |
13 | return new AuthorBean(); |
14 | } |
15 | } |
在没有使用 @PropertySource
注解指定加载的文件时,默认使用 application.properties
文件中与实体对象的属性相同的配置项。@PropertySources
注解优先级比较低,即使指定了加载的文件,但出现与 application.properties
文件相同的配置项时会被其覆盖。
自定义 YAML 资源文件属性配置
- 创建
user.yml
文件,进行属性配置
1 | # 配置 user 对象的值 |
2 | demo: |
3 | user: |
4 | name: star |
5 | age: 22 |
6 | desc: good boy! |
- 使用注解标记
User.java
对象文件
1 | /** |
2 | * UserConfig |
3 | * |
4 | * @author star |
5 | **/ |
6 |
|
7 | "demo.user") // 前缀名注释必须有,不然会报错 (prefix = |
8 | "classpath:user.yml",encoding = "utf-8") (value = |
9 | public class User { |
10 | // @Value() 注解必须要 |
11 | "${name}") ( |
12 | private String name; |
13 | |
14 | "${age}") ( |
15 | private int age; |
16 | |
17 | "${desc}") ( |
18 | private String desc; |
19 | |
20 | public String getName() { |
21 | return name; |
22 | } |
23 | |
24 | public void setName(String name) { |
25 | this.name = name; |
26 | } |
27 | |
28 | public int getAge() { |
29 | return age; |
30 | } |
31 | |
32 | public void setAge(int age) { |
33 | this.age = age; |
34 | } |
35 | |
36 | public String getDesc() { |
37 | return desc; |
38 | } |
39 | |
40 | public void setDesc(String desc) { |
41 | this.desc = desc; |
42 | } |
43 | } |
多环境配置
application-dev.properties
: 开发环境application-prod.properties
: 生产环境
Spring Boot 通过 application.roperties
文件,设置 spring.profiles.active
属性加载相应的文件,如:spring.profiles.active=dev
。
注意:Spring Boot 根据环境激活配置文件的规则是,默认加载 application.properties
文件,当此文件配置了 spring.profiles.active=xxx
后,会加载 application-xxx.properties
文件中的配置项,并覆盖 application.properties
中相同的配置项。
最后
- 使用 YAML 文件时,属性值和冒号中间必须要有空格。
- YAML 文件在配置中文值时,读取不会出现乱码问题;properties 文件配置中文值,读取会出现乱码。因为 Spring Boot 是以
iso-8859-1
的编码格式读取 properties 文件。