1. SpringBoot 配置文件格式
1. properties
2. yml
properties 优先级高于 yml。
自动识别的配置文件:bootstrap.yml 和 application.yml,bootstrap.yml 先于 application.yml 加载,一般用于系统级别的配置,application.yml 一般用于项目级别的配置
Springboot 官方的配置:https://docs.spring.io/spring-boot/docs/current/reference/html/application-properties.html#appendix.application-properties.web
2. @Value
读取单个配置文件
spring:
application:
name: yqa
@Value("${spring.application.name}")
private String appName;
引号的问题:
str1: hello\nworld
str2: 'hello\nworld'
str3: "hello\nworld"
@Value("${str1}")
public String str1;
@Value("${str2}")
public String str2;
@Value("${str3}")
public String str3;
@RequestMapping("/quote")
public void quote(){
System.out.println(str1);
System.out.println(str2);
System.out.println(str3);
}
结论:默认不用引号,单引号中特殊字符还是字面的意思,双引号会进行转义
3. @ConfigurationProperties
1. 对象的配置和读取
1. 配置文件
# 第一种方式
dog1:
name: yq
age: 29
#第二种方式
dog2: { name : yl, age : 27}
第二种方式不常见,在读取时候,只要 @ConfigurationProperties(prefix = "dog2") 就可以了
2. 配置实体类
package com.demo.config;
import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.stereotype.Component;
@Data
@Component
@ConfigurationProperties(prefix = "dog1")
public class Dog {
private String name;
private int age;
}
3. 引用
@Autowired
private Dog dog;
@RequestMapping("obj/quote")
public void test1(){
System.out.println(dog.getAge());
System.out.println(dog.getName());
}
2. 集合的配置和读取
1. 配置文件
# 第一种方式
cat1:
list:
- yq
- yl
- pz
#第二种方式
cat2: { list: [ yl, yq, pz] }
2. 配置实体类
import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.stereotype.Component;
import java.util.List;
@Data
@Component
@ConfigurationProperties(prefix = "cat1")
//@ConfigurationProperties(prefix = "cat2")
public class Cat {
private List<String> list;
}
3. 引用
@Autowired
private Cat cat;
@RequestMapping("/cat/quote")
public void test2(){
System.out.println(cat.getList());
}
4. Environment
org.springframework.core.env.Environment
引用可以直接引用配置文件
1. 配置文件
spring:
application:
name: yqa
2. 读取配置
@Autowired
private Environment environment;
@RequestMapping("/env/quote")
public void test3(){
System.out.println(environment.getProperty("spring.application.name"));
}
5. @PropertySource
上述 @ConfigurationProperties,@Value 默认都是读取主配置文件,也就是默认配置文件 application.yml、bootstrap.yml 等。通过 @PropertySource 可以引入指定的配置文件。
1. 读取 .properties 文件
1. 自定义配置文件
pro.test=我是测试
创建一个 my.properties 文件,放在 Springboot 默认的静态资源目录下,也就是 resource 目录下
2. @PropertySource 引入配置文件
@Data
@Component
@ConfigurationProperties(prefix = "chicken")
@PropertySource(value = "classpath:my.properties", encoding = "utf-8")
public class Chicken {
private String name;
private String age;
}
这个注解可以用在启动类上,也可以用在其他 Spring 可以扫描到的类上,然后就可以像默认的 application.properties 配置文件中的配置一样使用。
3. 使用示例
@Value("${pro.test}")
private String proTest;
@Autowired
private Chicken chicken;
@RequestMapping("/self/quote")
public void test4(){
System.out.println(proTest);
System.out.println(chicken.getName() + ";" + chicken.getAge());
}
2. 读取 .yml 文件
默认是不允许读取指定 yml 配置文件的,不过在 Spring 4.3 后通过引入 PropertySourceFactory 接口可以实现。
1. 创建 yml 配置文件工厂类
public class YamlPropertySourceFactory implements PropertySourceFactory {
@Override
public PropertySource<?> createPropertySource(@Nullable String name, EncodedResource resource) throws IOException {
Properties propertiesFromYaml = loadYamlIntoProperties(resource);
String sourceName = name != null ? name : resource.getResource().getFilename();
return new PropertiesPropertySource(sourceName, propertiesFromYaml);
}
private Properties loadYamlIntoProperties(EncodedResource resource) throws FileNotFoundException {
try {
YamlPropertiesFactoryBean factory = new YamlPropertiesFactoryBean();
factory.setResources(resource.getResource());
factory.afterPropertiesSet();
return factory.getObject();
} catch (IllegalStateException e) {
// for ignoreResourceNotFound
Throwable cause = e.getCause();
if (cause instanceof FileNotFoundException)
throw (FileNotFoundException) e.getCause();
throw e;
}
}
}
2. 创建 yml 配置文件
yq.yml:
person:
name: yq
age: 29
home: minhang
3. 引入自定义的 yq.yml 配置文件
import com.demo.factory.YamlPropertySourceFactory;
import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.context.annotation.PropertySource;
import org.springframework.stereotype.Component;
@Data
@Component
@ConfigurationProperties(prefix = "person")
@PropertySource(value = "classpath:yq.yml", encoding = "utf-8", factory = YamlPropertySourceFactory.class)
public class Person {
private String name;
private String age;
private String home;
}
这里通过 PropertySource 注解的 factory 属性,使用自定义的 YamlPropertySourceFactory。
4. 引入使用
@Autowired
private Person person;
@RequestMapping("/self/yml")
public void test5(){
System.out.println(person.getName() + ";" + person.getAge() + ";" + person.getHome());
}
6. 多环境配置文件
1. 配置文件选择环境
2. 启动命令行选择环境
java -jar .\springboot-yml-0.0.1-SNAPSHOT.jar --spring.profiles.active=test
3. 各种配置的优先级
以下是常用的 Spring Boot 配置形式及其加载顺序(优先级由高到低):
-
命令行参数
-
来自 java:comp/env 的 JNDI 属性
-
Java 系统属性(System.getProperties())
-
操作系统环境变量
-
RandomValuePropertySource 配置的 random.* 属性值
-
配置文件(YAML文件、Properties 文件)
-
@Configuration 注解类上的 @PropertySource 指定的配置文件
-
通过SpringApplication.setDefaultProperties 指定的默认属性
以上所有形式的配置都会被加载,当存在相同配置内容时,高优先级的配置会覆盖低优先级的配置;存在不同的配置内容时,高优先级和低优先级的配置内容取并集,共同生效,形成互补配置。
4. 属性占位符
app.name=MyApp
app.description=${app.name} is a Spring Boot application written by ${username:Unknown}
7. Springboot 配置文件加载
1. 官网描述
官方介绍 24.3 章:https://docs.spring.io/spring-boot/docs/2.0.3.RELEASE/reference/htmlsingle/
这里的 file:./
,指的是项目根目录,如果是多模块项目,也是最外层目录,而不是模块目录。对于 jar 包来讲,file:./
则是和 jar 包同目录级。而 classpath 则是资源目录,也就是 resource 目录下的文件,这里不仅有模块本身,还包括 jar 包的资源目录。
这里描述了 springboot 默认加载的配置文件,共有四个位置的配置文件被加载。所有配置文件全部加载,如果有共同的属性配置,高优先级覆盖低优先级。
优先级:file:./config/ > file:./ > classpath:/config/ > classpath:/
2. 对依赖的配置文件加载问题
上述加载的四个配置文件处,每处只能加载一个。
使用配置属性来查看配置文件加载情况:
logging:
level:
org:
springframework:
boot:
context:
config:
ConfigFileApplicationListener: trace
对于以下依赖:
启动 ArticleMain 启动类,打印日志:
源码看 ConfigFileApplicationListener
中,看不懂也懒得看。
发现会加载依赖中的配置文件 application.properties,当本项目配置与依赖有相同的 application.yml 时,优先加载本项目的 application.yml。
也可以通过 environment 来查看具体加载了哪些属性:
3. 总结
-
默认加载的四个位置拥有相同的配置文件,比如 application.yml,可以同时存在,属性互补。相同属性优先级高的位置说了算。
-
四个位置中,每个位置可以加载四个文件,分别是 application.properties、application.xml、application.yml、application.yaml,前后按优先级。
-
会加载依赖包的 classpath 也就是 resource 下配置文件,前提是项目本身没有这个配置文件,有点话就有限加载自己的。
-
如果两个依赖都有这个配置,那么添加依赖的顺序,先添加的依赖优先。
-
优先级
-
位置优先级:file:./config/ > file:./ > classpath:/config/ > classpath:/
-
文件类型优先级:properties > xml > yml > yaml
位置优先级 > 文件类型优先级
-
-
所有配置文件的配置项,最后都是加载到 Environment 中。
-
bootstrap.yml 目前不在讨论范围内,这个优先级最高,由父 springApplication 加载。