How does ApplicationContextAware work in Spring?

后端 未结 4 541
醉话见心
醉话见心 2020-12-22 16:42

In spring, if a bean implements ApplicationContextAware, then it is able to access the applicationContext. Therefore it is able to get other beans.

4条回答
  •  清酒与你
    2020-12-22 17:21

    Spring source code to explain how ApplicationContextAware work
    when you use ApplicationContext context = new ClassPathXmlApplicationContext("applicationContext.xml");
    In AbstractApplicationContext class,the refresh() method have the following code:

    // Prepare the bean factory for use in this context.
    prepareBeanFactory(beanFactory);
    

    enter this method,beanFactory.addBeanPostProcessor(new ApplicationContextAwareProcessor(this)); will add ApplicationContextAwareProcessor to AbstractrBeanFactory.

    protected void prepareBeanFactory(ConfigurableListableBeanFactory beanFactory) {
            // Tell the internal bean factory to use the context's class loader etc.
            beanFactory.setBeanClassLoader(getClassLoader());
            beanFactory.setBeanExpressionResolver(new StandardBeanExpressionResolver(beanFactory.getBeanClassLoader()));
            beanFactory.addPropertyEditorRegistrar(new ResourceEditorRegistrar(this, getEnvironment()));
            // Configure the bean factory with context callbacks.
            beanFactory.addBeanPostProcessor(new ApplicationContextAwareProcessor(this));
    ...........
    

    When spring initialize bean in AbstractAutowireCapableBeanFactory, in method initializeBean,call applyBeanPostProcessorsBeforeInitialization to implement the bean post process. the process include inject the applicationContext.

    @Override
        public Object applyBeanPostProcessorsBeforeInitialization(Object existingBean, String beanName)
                throws BeansException {
            Object result = existingBean;
            for (BeanPostProcessor beanProcessor : getBeanPostProcessors()) {
                result = beanProcessor.postProcessBeforeInitialization(result, beanName);
                if (result == null) {
                    return result;
                }
            }
            return result;
        }
    

    when BeanPostProcessor implement Objectto execute the postProcessBeforeInitialization method,for example ApplicationContextAwareProcessor that added before.

    private void invokeAwareInterfaces(Object bean) {
            if (bean instanceof Aware) {
                if (bean instanceof EnvironmentAware) {
                    ((EnvironmentAware) bean).setEnvironment(this.applicationContext.getEnvironment());
                }
                if (bean instanceof EmbeddedValueResolverAware) {
                    ((EmbeddedValueResolverAware) bean).setEmbeddedValueResolver(
                            new EmbeddedValueResolver(this.applicationContext.getBeanFactory()));
                }
                if (bean instanceof ResourceLoaderAware) {
                    ((ResourceLoaderAware) bean).setResourceLoader(this.applicationContext);
                }
                if (bean instanceof ApplicationEventPublisherAware) {
                    ((ApplicationEventPublisherAware) bean).setApplicationEventPublisher(this.applicationContext);
                }
                if (bean instanceof MessageSourceAware) {
                    ((MessageSourceAware) bean).setMessageSource(this.applicationContext);
                }
                if (bean instanceof ApplicationContextAware) {
                    ((ApplicationContextAware) bean).setApplicationContext(this.applicationContext);
                }
            }
        }
    

提交回复
热议问题