属性赋值
通常使用属性赋值的方式有:
- xml的Bean中使用property属性
- xml中使用SpEL#{}
- xml中使用${}读取配置文件 前提得在xml中配置
- 可以替代的注解方案有:
- @value 默认支持基本数值,SpEl#{} 和 ${} > 支持${}的前提 使用注解@PropertySource:读取外部配置文件中的k/v保存到运行的环境变量中;加载完外部的配置文件以后使用${}取出配置文件的值
运行环境的遍历是什么呢:
//这样可以获取到配置文件的属性哦~ ConfigurableEnvironment environment = applicationContext.getEnvironment(); String property = environment.getProperty("person.nickName"); System.out.println(property);
自动装配相关注解与底层原理
> Spring利用依赖注入(DI),完成对IOC容器中中各个组件的依赖关系赋值;
@Autowired、@Qualifier、@Primary、JSR250相关注解[@Resource]、JSR330相关注解[@Inject]
@Autowired 自动注入规则:
- 默认有限按照类型去容器中找对应的组件
- 如果找到多个相同类型的组件,再将属性的名称作为组件的id去容器中查找
- Qualifier("beanId") 指定需要装配的组件id,而不使用属性名
- 使用自动装配一定要将属性赋值好,没有就会报错 可以通过使用@Autowired(required=false);避免这个问题
- 使用@Primary:让Spring进行自动装配的时候,默认使用首选的bean;
@Resource :可以和@Autowired一样实现自动装配的功能,默认是按照属性名称去查找Bean;没有能支持Primary的功能以及@Autowired(required=false)的功能
@Inject : 功能和@Autowired一样,默认支持@primary的功能,但是不支持@Autowired(required=false)的类似功能
JSR250和JSR330是Java规范,而Autowired是Spring框架自己自定义的
AutowiredAnnotationBeanPostProcessor:解析完成自动装配功能 支持上面的注解;细节代码如下:
@SuppressWarnings("unchecked") public AutowiredAnnotationBeanPostProcessor() { this.autowiredAnnotationTypes.add(Autowired.class); this.autowiredAnnotationTypes.add(Value.class); try { this.autowiredAnnotationTypes.add((Class extends Annotation>) ClassUtils.forName("javax.inject.Inject", AutowiredAnnotationBeanPostProcessor.class.getClassLoader())); logger.info("JSR-330 'javax.inject.Inject' annotation found and supported for autowiring"); } catch (ClassNotFoundException ex) { // JSR-330 API not available - simply skip. } }
> 注意:CommonAnnotationBeanPostProcessor 支持 JSR250
关于@Autowired:
- 标注的位置: 构造器、方法、参数、属性[PS:这些都是从容器中获取参数组件的值]
- 详细使用方法:
- 2.1 标注在方法位置:@Bean+方法参数,参数默认从容器中获取[可以不写@AutoWired也能完成自动装配]
//@Autowired //标注在方法,Spring容器创建当前对象,就会调用方法,完成赋值; //方法使用的参数,自定义类型的值从ioc容器中获取 public void setCar(Car car) { this.car = car; }
- 2.2 标注在构造器上:如果组件只有一个有参构造器,那么@Autowired也可以省略且能完成自动装配
//默认加在ioc容器中的组件,容器启动会调用无参构造器创建对象,再进行初始化赋值等操作@Componentpublic class Boss { private Car car; //构造器要用的组件,都是从容器中获取 public Boss(Car car){ this.car = car; System.out.println("Boss...有参构造器"); } public Car getCar() { return car; } @Override public String toString() { return "Boss [car=" + car + "]"; }}
2.3 标注在参数位置:与标注在方法上一致
//AutoWired可以不写 @Bean public Color color(@AutoWired Car car){ Color color = new Color(); color.setCar(car); return color; }
拓展 : 自定义组件如何使用Spring容器底层的一些组件(applicationContext,Beanfactory等等)?
自定义组件实现xxxAware接口;在创建对象的时候,会调用接口规定的方法注入相关组件 Aware[Interface]-->把Spring底层的一些组件注入到自定义的Bean中
每一个 xxxxAware 都会对应一个 xxxProcessor 从而能让底层组件成功注入到自定义bean中
![属性赋值与自动装配](http://p2.ttnews.xyz/loading.gif)
閱讀更多 Java程序猿鼓勵師 的文章