spring

【Spring源码】12.IOC之Bean初始化之生命周期钩子的

2022-01-27  本文已影响0人  天还下着毛毛雨
image

前言

在属性注入之后,下一个阶段就是bean的生命周期钩子调用, 和实现各种aware接口的方法调用。

  1. 1.((BeanNameAware) bean).setBeanName(beanName);
    2.((BeanClassLoaderAware) bean).setBeanClassLoader(bcl);
    3.((BeanFactoryAware) bean).setBeanFactory(AbstractAutowireCapableBeanFactory.this);
    
  2. // ApplicationContextAwareProcessor : EnvironmentAware、EmbeddedValueResolverAware、ResourceLoaderAware、
    //                               ApplicationEventPublisherAware、MessageSourceAware、ApplicationContextAware 接口的调用
    // InitDestroyAnnotationBeanPostProcessor : @ProConstrcut 方法的调用
    // ConfigurationClassPostProcessor.ImportAwareBeanPostProcessor : 如果该类被B类@import进来,那么该方法会传入B类的注解元数据AnnotationMetadata
    
  3. // 1. 执行InitializingBean.afterPropertiesSet();
    // 2. 执行@InitMethod修饰的方法
    

代码在依赖注入之后

image

1.invokeAwareMethods

如果你的bean 实现了BeanNameAware,BeanClassLoaderAware,BeanFactoryAware 接口,那么这个阶段就会调用 bean 实现自这三个接口的方法。

  1. ((BeanNameAware) bean).setBeanName(beanName);
  2. ((BeanClassLoaderAware) bean).setBeanClassLoader(bcl);
  3. ((BeanFactoryAware) bean).setBeanFactory(AbstractAutowireCapableBeanFactory.this);
image

2. ApplicationContextAwareProcessor 调用其他Aware接口

如果bean实现了,EnvironmentAware,EmbeddedValueResolverAware,ResourceLoaderAware,ApplicationEventPublisherAware,MessageSourceAware,ApplicationContextAware 等接口,

那么ApplicationContextAwareProcessor类的applyBeanPostProcessorsBeforeInitialization方法, 会调用 bean 实现自这几个接口的方法。并传入参数。

image image image
  1. InitDestroyAnnotationBeanPostProcessor调用的@ProConstrcut 方法。

    还有InitDestroyAnnotationBeanPostProcessor这个类 也在这里起作用, 同样是applyBeanPostProcessorsBeforeInitialization方法,会调用bean中带有@ProConstrcut 注解的方法。

    image

前面讲过bean的方法如果有 @@ProConstrcut注解和@PreDestory注解的话,那么会被 InitDestroyAnnotationBeanPostProcessor这个类 收集起来。这里调用,就会去拿之前收集好的方法进行调用。

image

LifecycleElement类 封装了 Method对象,这里直接拿Method对象反射调用方法。

image

3. ImportAwareBeanPostProcessor 传入元数据

如果Bean是被A类的Bean 是被B类 用@Import注解 导进来的话, 如果A类实现 ImportAware接口,那么 ImportAwareBeanPostProcessor.postProcessBeforeInitialization方法就会在这个阶段 调用 A类 实现 自 ImportAware 接口的setImportMetadata方法,传入B类的元数据给 bean。

image

示例代码:

ImportBean这个类 导入BeImportBean 这个类

@Component
@Import(BeImportBean.class)
public class ImportBean {

    @Component
    class MemberClass {

    }
}

BeImportBean 实现ImportAware接口,setImportMetadata传入的参数就是 ImportBean的元数据。

public class BeImportBean implements ImportAware {


    @Override
    public void setImportMetadata(AnnotationMetadata importMetadata) {

    }
}

4. 执行InitializingBean.afterPropertiesSet() 和 @InitMethod修饰的方法

image

4.1 InitializingBean.afterPropertiesSet()

image

4.2 执行@InitMethod方法

image

一开始找方法

image

反射

image

5. 添加事件监听器

最后面还有两个BeanPostProcessor的运用,其中一个运用的地方就是 ApplicationListenerDetector这个类会判断当前Bean是否 一个事件监听器,是的话加入到事件管理器,后续对应事件触发的话才能通知到 这个Bean。

image image

6. aop的入口

另外一个运用就是 AbstractAutoProxyCreator 这个BeanPostProcessor子类 会判断 当前Bean是否命中切面,命中切面的话 需要生成代理。

image image

总结

到这里, bean的属性 有值,各种初始化的方法 都调用了,如果命中切面,aop就为它生成代理, 如果没有命中, 就返回原生的bean。一个完整的bean 就创建完, 可以被 其他的bean 依赖使用了。

上一篇下一篇

猜你喜欢

热点阅读