@ConfigurationProperties
其主要作用是将配置文件中特定属性转换为Java对象,方便管理和使用。
其可以作为单独的Bean使用,也可以配合@Configuration使用(好像有点废话了)
@Configuration注解使用
SpringBoot 自定义starter组件
注:本文以将aliyun短信sdk中所需配置提升到Springboot配置文件中为例
与配置文件对应关系
application.yml配置文件
spring:
aliyun:
domain: dysmsapi.aliyuncs.com
regionid: cn-hangzhou
accessKeyId: ********
secret: ******************
version: 2017-05-25
对应Class
import org.springframework.boot.context.properties.ConfigurationProperties;
@ConfigurationProperties(prefix = "spring.aliyun")
public class AliyunProperties {
private String domain;
private String version;
private String regionid;
private String accessKeyId;
private String secret;
public String getDomain() {
return domain;
}
public void setDomain(String domain) {
this.domain = domain;
}
public String getVersion() {
return version;
}
public void setVersion(String version) {
this.version = version;
}
public String getRegionid() {
return regionid;
}
public void setRegionid(String regionid) {
this.regionid = regionid;
}
public String getAccessKeyId() {
return accessKeyId;
}
public void setAccessKeyId(String accessKeyId) {
this.accessKeyId = accessKeyId;
}
public String getSecret() {
return secret;
}
public void setSecret(String secret) {
this.secret = secret;
}
}
至此,当你的AliyunProperties.java在Spring的扫描路径(scanBasePackages)下时,配置文件到对象的配置就已经完成了(注意并不能直接使用)。
在SpringBoot项目中的使用
基于Spring的IOC的思想,此时AliyunProperties是不能被别的Bean所注入的,原因因为:
@Target({ ElementType.TYPE, ElementType.METHOD })
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface ConfigurationProperties {
@AliasFor("prefix")
String value() default "";
@AliasFor("value")
String prefix() default "";
boolean ignoreInvalidFields() default false;
boolean ignoreUnknownFields() default true;
}
其并未声明未Spring的组件,如果想像其他Bean那样直接交由IOC容器进行实例化,声明此类时加上@Component注解标注其为Bean组件即可:
@ConfigurationProperties(prefix = "spring.aliyun")
@Component //将其声明为Bean组件,注入到IOC容器中
public class AliyunProperties {
//... 代码在上面
}
在@Configuration注解下使用实例:
import com.aliyuncs.DefaultAcsClient;
import com.aliyuncs.IAcsClient;
import com.aliyuncs.profile.DefaultProfile;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.util.StringUtils;
/**
* 阿里云服务客户端
*/
@Configuration
public class AcsClient {
// 阿里云配置
private static DefaultProfile profile = null;
private static AcsSmsClient acsSmsClient = null;
@Bean
public IAcsClient client(AliyunProperties aliyunProperties){
// 省略具体实现,不影响解读
}
}
作为普通Bean组件使用
@RestController
@RequestMapping("/sms")
public class SmsController {
@Autowired
AliyunProperties aliyunProperties;
}
通过以上两种使用方式,可以看到,在AliyunProperties这个Bean使用的时候属性已经是配置文件里的内容,也就是说AliyunProperties实例化后的属性是经过修改的(默认全为空),那么是什么时候修改的呢?这就需要了解@ConfigurationProperties的实现原理(关键点:Spring的Bean后处理器)。
其实在SpringBoot中还有个注解与@ConfigurationProperties比较相近@EnableConfigurationProperties, 这两者是配合使用的,@EnableConfigurationProperties注解是将指定的@ConfigurationProperties标注的类Bean化,这种实现方式AliyunProperties.java就不需要再@Component去声明了。
import com.aliyuncs.DefaultAcsClient;
import com.aliyuncs.IAcsClient;
import com.aliyuncs.profile.DefaultProfile;
import org.springframework.context.annotation.Bean;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Configuration;
import org.springframework.util.StringUtils;
/**
* 阿里云服务客户端
*/
@Configuration
@EnableConfigurationProperties({AliyunProperties.class})
public class AcsClient {
// 阿里云配置
private static DefaultProfile profile = null;
private static AcsSmsClient acsSmsClient = null;
@Bean
public IAcsClient client(AliyunProperties aliyunProperties){
// 省略具体实现,不影响解读
}
}
@Value的使用
首先说明一点,@Value是spring-bean内提供的属性装配注解;
其使用方式有两种:
${ property : default_value } // 读取配置文件内属性(无需默认值的时候请连“:”一并省略,参见下面代码)
#{ obj.property? :default_value } // 读取对象属性(Bean)或者方法返回值(需要在前面增加@,如#{@obj.getValue()})
使用方式较为简单,在需要的Bean内直接使用注解即可
import org.springframework.beans.factory.annotation.Value;
@Service
public class DemoServiceImpl implements DemoService {
@Value("${base.server.serverurl}")
public String serverurl;
}