平常使用的@Autowired
等注解进行依赖注入主要针对的是两个 bean 之间的依赖关系,当想要将基础数据类型或者 Java 包装类注入到 bean 中时,为了避免将值硬编码到代码中,有两种方式:属性占位符和 Spring 表达式语言。
属性占位符(Property placeholder)
在配置文件中声明对应值引入到 Spring 中。
从 Environment 中检索属性
@Configuration
@PropertySource("classpath:/com/soundsystem/app.properties")
public class ExpressiveConfig {
@Autowired
Environment env;
@Bean
public BlankDisc disc() {
return new BlankDisc(
env.getProperty("disc.title"),
env.getProperty("disc.artist")
);
}
}
app.properties 属性文件会加载到 Spring 的 Environment 中,通过getProperty()
方法获取到属性值。
getProperty()
方法:
- String getProperty(String key):获取 key 对应的属性值。
- String getProperty(String key, String defualtValue):添加默认值。
- T getProperty(String key, Class
type):将值解析为对应类型。 - T getProperty(String key, Class
type, T defaultValue):添加默认值。
其他方法:
- getRequiredProperty():获取必需的属性值,如果属性不存在,则抛出异常。
- containsProperty():检查某个属性是否存在。
- getPropertyAsClass():将属性解析为类。
- String[] getActiveProfiles():返回激活 profile 名称的数组。
- String[] getDefaultProfiles():返回默认 profile 名称的数组。
- boolean acceptsProfiles(String... profiles):如果 environment 支持给定 profile 的话,就返回true。
通过占位符装配属性
使用占位符需要配置 PropertySourcesPlaceholderConfigurer bean,它能够基于 Spring Environment 及其属性源来解析占位符。
@Bean
public PropertySourcesPlaceholderConfigurer placeholderConfigurer() {
return new PropertySourcesPlaceholderConfigurer();
}
占位符的形式为使用${ ... }
包装的属性名称。如果使用组件扫描和自动装配来创建和初始化应用组件,可以使用@Value
注解,只需将构造器改成如下所示:
public BlankDisc(
@Value("${disc.title}") String title,
@Value("${disc.artist}") String artist) {
this.title = title;
this.artist = artist;
}
Spring 表达式语言(SpEL)
SpEL 实现一些复杂的操作例如运算、调用方法等。
SpEL 表达式要放到#{ ... }
之中。
可以通过 systemProperties 对象引用系统属性,因此上面的示例使用 SpEL 可以修改为如下所示:
public BlankDisc(
@Value("#{systemProperties['disc.title']}") String title,
@Value("#{systemProperties['disc.artist']}") String artist) {
this.title = title;
this.artist = artist;
}
SpEL 还有其他用法,这里不再赘述。