使用场景
依赖注入方式:
1 通过EnvironmentAware方式
2 通过@Autowired的方式
用于属性占位符处理
getProperty() 这里有多个方法,带有targetType的方法是可以进行类型转换的方法,但是不一定能转换成功,只是尝试去抓换,如果转换失败则返回NULL。
这里getProperty最终是通过PropertySourcesPropertyResolver进行值的获取。
用于转换Spring配置类型
其实是AbstractPropertyResolver进行处理的。
用于存储Spring配置属性源(PropertySource)
在AbstractEnvironment中有一个属性propertySources:
其实内部就是一个可变的资源:
除了我们注册的PropertySources,Environment在初始化的时候还帮我们添加了systemEnvironment和systemProperties。
上面这些资源何时被加载呢?我们可以看到是选取的第一个PropertyResolver,如果能获取到值就返回了。如果存在同名资源采用什么顺序呢?因为是成功处理就返回,所以说添加PropertySources的顺序就是优先级,可以参考addFirst,addLast.PropertySources在容器启动后修改是不会更新@Value的,不具备动态更新能力。
用于ProFiles状态的维护
PropertySouce 外部化配置
通过API
public class MyPropertySource extends MapPropertySource {
@SuppressWarnings({"unchecked", "rawtypes"})
public MyPropertySource(String name, Properties source) throws IOException {
super(name, (Map) source);
}
protected MyPropertySource(String name, Map<String, Object> source) {
super(name, source);
}
@Override
public Object getProperty(String name) {
return super.getProperty(name);
}
}
PropertySource my = new MyPropertySource("my-properties", DefaultPropertiesLoader.load());
environment.getPropertySources().addFirst(my);
通过注解的方式
@PropertySource("classpath://META-INF/default.properties")
public class MyProperties {
@Value("${user.id}")
private String id;
@Value("${user.name}")
private String name;
@Value("${user.resource}")
private String resource;
@Override
public String toString() {
return "MyProperties{" +
"id='" + id + '\'' +
", name='" + name + '\'' +
", resource='" + resource + '\'' +
'}';
}
}
也可以通过配置PropertySource 的PropertySourceFactory的方式
public class YamlPropertySourceFactory implements PropertySourceFactory {
@Override
public PropertySource<?> createPropertySource(String name, EncodedResource resource) throws IOException {
YamlPropertiesFactoryBean yamlPropertiesFactoryBean = new YamlPropertiesFactoryBean();
yamlPropertiesFactoryBean.setResources(resource.getResource());
Properties yamlProperties = yamlPropertiesFactoryBean.getObject();
return new PropertiesPropertySource(name, yamlProperties);
}
}
@PropertySource(
name = "yamlPropertySource",
value = "classpath:/META-INF/user.yaml",
factory = YamlPropertySourceFactory.class)
public class AnnotatedYamlPropertySourceDemo {
}