spring IoC (八)Bean对IoC容器的感知
容器管理的Bean一般不需要了解容器的状态和直接使用容器,但在某些情况下,是需要在Bean中直接
对IoC容器进行操作的,这时候,就需要在Bean中设定对容器的感知。Spring IoC容器也提供了该功能,它
是通过特定的aware接口来完成的。例如BeanNameAware、BeanFactorAware、ApplicationContextAware
、MessageSourceAware、ResourceLoaderAware等。
在 Bean实例化后,初始化前会调用BeanPostProcessor.postProcessBeforeInitialization
AbstractAutowireCapableBeanFactory.applyBeanPostProcessorsBeforeInitialization() -->
BeanPostProcessor.postProcessBeforeInitialization(Object, String)
例如ApplicationContextAwareProcessor中
1 public Object postProcessBeforeInitialization(final Object bean, String beanName) throws BeansException { 2 AccessControlContext acc = null; 3 4 if (System.getSecurityManager() != null && 5 (bean instanceof EnvironmentAware || bean instanceof EmbeddedValueResolverAware || 6 bean instanceof ResourceLoaderAware || bean instanceof ApplicationEventPublisherAware || 7 bean instanceof MessageSourceAware || bean instanceof ApplicationContextAware)) { 8 acc = this.applicationContext.getBeanFactory().getAccessControlContext(); 9 } 10 11 if (acc != null) { 12 AccessController.doPrivileged(new PrivilegedAction<Object>() { 13 public Object run() { 14 invokeAwareInterfaces(bean); 15 return null; 16 } 17 }, acc); 18 } 19 else { 20 invokeAwareInterfaces(bean); 21 } 22 23 return bean; 24 } 25 26 private void invokeAwareInterfaces(Object bean) { 27 if (bean instanceof Aware) { 28 if (bean instanceof EnvironmentAware) { 29 ((EnvironmentAware) bean).setEnvironment(this.applicationContext.getEnvironment()); 30 } 31 if (bean instanceof EmbeddedValueResolverAware) { 32 ((EmbeddedValueResolverAware) bean).setEmbeddedValueResolver( 33 new EmbeddedValueResolver(this.applicationContext.getBeanFactory())); 34 } 35 if (bean instanceof ResourceLoaderAware) { 36 ((ResourceLoaderAware) bean).setResourceLoader(this.applicationContext); 37 } 38 if (bean instanceof ApplicationEventPublisherAware) { 39 ((ApplicationEventPublisherAware) bean).setApplicationEventPublisher(this.applicationContext); 40 } 41 if (bean instanceof MessageSourceAware) { 42 ((MessageSourceAware) bean).setMessageSource(this.applicationContext); 43 } 44 if (bean instanceof ApplicationContextAware) { 45 ((ApplicationContextAware) bean).setApplicationContext(this.applicationContext); 46 } 47 } 48 }