Spring注解开发之属性赋值和自动装配
属性赋值
@Value
bean定义
@Getter
@Setter
public class Person {
// 使用@Value
// 1. 基本数值
// 2. 可以写SpEL:#{}
// 3. 可以写${} 取出配置文件的值
@Value("Lebron")
private String name;
@Value("#{23+5}")
private int age;
}
配置类
@Configuration
public class MainConfigOfPropertyValues {
@Bean
public Person person(){
return new Person();
}
}
@PropertySource
配置类
@PropertySource(value = {"classpath:/person.properties"})
@Configuration
public class MainConfigOfPropertyValues {
@Bean
public Person person(){
return new Person();
}
}
bean定义
@Value("Lebron")
private String name;
@Value("#{23+5}")
private int age;
@Value("${person.nickName}")
private String nickname;
person.properties
person.nickName = king
自动装配
@Autowired
自动找到容器中的bean,优先根据id去找
@Autowired
BookDao bookDao2;
优先会找bookDao2的bean
-
构造器
默认加载IOC容器中的组件,容器启动会调用无参构造器,再进行初始化赋值
-
参数
-
方法
标注在方法上,spring容器创建当前对象,就会调用方法,完成赋值。方法实用的参数,自定义类型的值从IOC容器中获取。
-
属性
-
用@Bean标注的方法创建对象的时候,方法参数的值会从容器中获取。可以不用写@Autowired
都是从容器中获取组件。
@Qualifier
指定自动注入的bean组件id
@Qualifier("bookDao")
@Autowired
BookDao bookDao2;
只会去找id为bookDao的bean,没有则会报错
@Primary
优先加载某一类bean,即使有其他的id的bean,会优先primary的bean
@Repository
@Primary
public class BookDao {
private String label = "1";
public String getLabel() {
return this.label;
}
public void setLabel(String label) {
this.label = label;
}
@Override
public String toString() {
return "BookDao{" +
"label='" + this.label + '\'' +
'}';
}
}
注意:优先级:@Qualifier > @Primary > @Autowired
@Resource
JSR250注解
类似于@Autowired,默认按照名称来装配,可以用name属性指定
Aware
自定义组件想要使用Spring容器底层的一些组件(ApplicationContext,BeanFactroy),实现xxxAware,在创建对象的时候,会调用接口规定的方法注入相关组件。
xxxAware:功能使用xxxProcessor来实现的。
@Component
public class Red implements ApplicationContextAware, BeanNameAware, EmbeddedValueResolverAware {
private ApplicationContext applicationContext;
@Override
public void setBeanName(String s) {
System.out.println("当前bean的名字" + s);
}
@Override
public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
this.applicationContext = applicationContext;
System.out.println("当前容器"+applicationContext);
}
@Override
public void setEmbeddedValueResolver(StringValueResolver stringValueResolver) {
String s = stringValueResolver.resolveStringValue("${os.name} #{20*12}");
System.out.println("解析的字符串"+s);
}
}
spring源码中:
postProcessBeforeInitialization
if (!(bean instanceof EnvironmentAware)
&& !(bean instanceof EmbeddedValueResolverAware)
&& !(bean instanceof ResourceLoaderAware)
&& !(bean instanceof ApplicationEventPublisherAware)
&& !(bean instanceof MessageSourceAware)
&& !(bean instanceof ApplicationContextAware)) {...}
@Profile
spring可以根据当前环境,动态的激活和切换一系列组件的功能。
指定组件在那个环境的情况下,才能被注册到容器中。
@Profile("test")
@Bean("testDataSource")
public DataSource dataSource(){}
@Profile("dev")
@Bean("devDataSource")
public DataSource dataSource(){}
如上,加了环境标识的bean,只有这个环境被激活的时候才能注册到容器中。
如果写在配置类上,只有是指定的环境的时候,整个配置类里面的所有配置才能生效。
没有环境标识的bean,默认都是加载的。
- 使用命令行动态参数激活环境,在虚拟机参数位置加载 -Dspring.profiles.active=test
-
- 创建一个applicationContext
- 设置需要激活的环境
applicationContext.getEnvironment().setActiveProfiles("test","dev")
- 注册住配置类
applicationContext.register(MainConfigOfProfile.class)
- 启动刷新容器
application.refresh()