Spring Boot允许您外部化配置,这样您就可以在不同的环境中使用相同的应用程序代码。您可以使用各种外部配置源,包括Java属性文件、YAML文件、环境变量和命令行参数,通过外部化配置调整应用行为。
SpringBoot 提供的外部化配置有哪些优先级大的属性或覆盖优先级小的属性值
| 优先级 | 来源 | 说明 |
|---|---|---|
| 1 | Default properties (specified by setting SpringApplication.setDefaultProperties). | SpringApplication.setDefaultProperties设置 |
| 2 | @PropertySource annotations | @PropertySource指定的配置 |
| 3 | Config data (such as application.properties files). | application-XX.yml或Properties |
| 4 | RandomValuePropertySource | SpringBoot 默认提供随机数属性 具体实现类RandomValuePropertySourceEnvironmentPostProcessor |
| 5 | OS environment variables | 操作系统环境变量 具体实现类SystemEnvironmentPropertySourceEnvironmentPostProcessor |
| 6 | Java System properties (System.getProperties()). | jvm虚拟机环境变量 |
| 7 | JNDI attributes from java:comp/env | JNDI环境属性 |
| 8 | ServletContext init parameters | servlet上下文初始化参数 |
| 9 | ServletConfig init parameters | servlet配置初始化参数 |
| 10 | Properties from SPRING_APPLICATION_JSON | 通过环境变量或系统属性指定的spring.application.json 可以参考 |
| 11 | Command line arguments. | 命令行 |
| 12 | properties attribute on your tests | 通过@SpringBootTest指定的配置 |
| 13 | @TestPropertySource annotations on your tests | @TestProperty指定的配置 |
| 14 | Devtools global settings properties in the $HOME/.config/spring-boot directory when devtools is active | 通过Devtools 指定目录下的配置文件 |
- @Value 注解 通过注入获取配置属性参数
- Spring Environment 读取配置属性参数
- @ConfigurationProperties 加载外部配置装配成一个Bean
- @ConditionalOnProperty 判断
- XML配置文件属性占位符
- 实现EnvironmentPostProcessor接口
类图
- 自定义实现EnvironmentPostProcessor,并在Spring.factories文件中添加org.springframework.boot.env.EnvironmentPostProcessor=com.github.bearboy80.tomcat.MyEnvironmentPostProcessor
public class MyEnvironmentPostProcessor implements EnvironmentPostProcessor {
private final YamlPropertySourceLoader loader = new YamlPropertySourceLoader();
@Override
//关键点:实现逻辑处理,并加propertySoure 添加到environment中
public void postProcessEnvironment(ConfigurableEnvironment environment, SpringApplication application) {
Resource path = new ClassPathResource("com/example/myapp/config.yml");
PropertySource> propertySource = loadYaml(path);
environment.getPropertySources().addLast(propertySource);
}
private PropertySource> loadYaml(Resource path) {
Assert.isTrue(path.exists(), () -> "Resource " + path + " does not exist");
try {
return this.loader.load("custom-resource", path).get(0);
}
catch (IOException ex) {
throw new IllegalStateException("Failed to load yaml configuration from " + path, ex);
}
}
}
- 可以参考官方简单实现类:RandomValuePropertySourceEnvironmentPostProcessor
- 基于ApplicationEnvironmentPreparedEvent实现
- 基于ApplicationContextInitializer实现
- 基于ApplicationPreparedEvent事件实现
SpringBoot本身提供很好的机制来帮助我们实现自定义属性装载,建议如果扩展外部化属性,通过实现EnvironmentPostProcessor类来作扩展。



