Resumen personal en el proceso de inicialización del COI de primavera de 2019

Solo quiero que las grandes olas se lleven la arena y no pasen

Primero, permítanme hablar sobre mi comprensión personal del contenedor de primavera (hay un proyecto en todos los proyectos en el sitio web oficial de primavera llamado Spring Springframework, o Spring Framework para abreviar)

El marco de primavera es un contenedor que se utiliza para almacenar los objetos que entregamos a Spring para su gestión, denominados beans.

Los módulos principales se dividen principalmente en IOC y AOP (web, prueba, etc.)

La IOC también se denomina inversión DI de control e inyección de dependencia. La idea principal es el desacoplamiento. La inversión de control significa principalmente que solíamos necesitar programadores para crear un objeto a través de la nueva palabra clave y mantener las dependencias entre los objetos. Después de IOC, solo necesitamos entregar este objeto al contenedor. ayúdanos a crear y mantener dependencias entre objetos.

Y AOP, programación orientada a aspectos, separa y encapsula los módulos públicos de nuestro proyecto en un solo módulo, este módulo se llama aspecto, que también nace para el desacoplamiento en el pensamiento.

Usamos aop de dos maneras, la primera es spring aop configurada a través de archivos xml, y la segunda se abre mediante la anotación @Aspect.

Debe haber puntos de conexión (ejecución de expresión, dentro, etc.), puntos de corte, notificaciones (antes, después, envolvente, excepción) y entretejidos en un aspecto nuestro.

La diferencia es que el resorte aop se teje dinámicamente en tiempo de ejecución. El aspecto se teje estáticamente en el momento de la compilación. Cual depende de la preferencia personal

Entonces AOP depende de IOC, tanto IOC y AOP son dos partes (el sitio web oficial está separado), es mejor decir que AOP es parte de IOC, porque el ciclo de vida de springbean está acompañado por el análisis de AOP ( por ejemplo, el primer paso es a través de un postprocesador de BeanPostProcessor que se usa para completar una colección de objetos que necesitan ser proxiados para prepararse para mejoras posteriores).

 Lo primero que quiero presentar es el objeto BeanDefinition. El objetivo final de Spring es convertir el objeto Java ---> BeanDefinition ---> Spring Bean

 Por lo tanto, el objeto BeanDefinition y sus atributos y subclases son muy importantes. Presente esta imagen del sitio web oficial de Spring nuevamente

El Objeto Java llena los meta-atributos a través del contenedor Spring y se convierte en un objeto BeanDefinition. Después de un ciclo de vida completo, el Objeto Java se convierte en un Spring Bean para que usted lo use. El proceso y la implementación no requieren que lo hagamos.

El segundo punto introducido es el punto de extensión del contenedor Spring.

Los puntos de extensión son los siguientes

InitializingBean Spring Bean, una de las interfaces de devolución de llamada del ciclo de vida, Spring Web MVC inicializa y llena la propiedad Map para implementar esta interfaz 

Una de las interfaces de devolución de llamada para completar la inicialización del contenedor SmartLifecycle Spring 

La configuración automática de ImportSelector Spring Boot (ensamblaje automático que no es de Spring) implementa esta interfaz

ImportBeanDefinitionRegistrar MyBatis integra Spring para realizar el proceso de escaneo de la propiedad MapperScanner de esta interfaz -> Objeto Proxy -> Spring Bean

BeanFactoryPostProcessor Postprocesador BeanFactory

BeanDefinitionRegistryPostProcessor extiende BeanFactoryPostProcessor Postprocesador de fábrica de BeanFactory

ConfigurationClassPostProcessor implementa BeanDefinitionRegistryPostProcessor Postprocesador de fábrica BeanFactory solo integrado clase de implementación
A continuación, observe el tiempo de ejecución de estas tres clases (clases de implementación) en el código fuente

new AnnotationConfigApplicationContext(AppConfig.class);
this();//第一步 初始化 beanFactory 工厂
register(annotatedClasses); // 注册配置类
refresh(); // 如下 
//准备工作包括设置启动时间,是否激活标识位,初始化属性源(property,source)配置
prepareRefresh();
//获取到 DefaultListableBeanFactory 对象
//已经注册过了
ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory();
//传入 beanFactory 调用处理器对Bean工厂做一些标准的配置
prepareBeanFactory(beanFactory);
//空方法
postProcessBeanFactory(beanFactory);
//执行自定义的BeanFactoryProcessor和内置的BeanFactoryProcessor
// 完成扫描和解析 object --  > beanDefinition
invokeBeanFactoryPostProcessors(beanFactory);//开始执行BeanFactory的后置处理器扩展点(策略模式)
registerBeanPostProcessors(beanFactory);//开始执行BeanFactory 的后置处理器
initMessageSource();
initApplicationEventMulticaster();
onRefresh();
registerListeners();
//实例化所有的非懒加载单例
//bean生命周期
finishBeanFactoryInitialization(beanFactory);
finishRefresh();

invokeBeanFactoryPostProcessors (beanFactory);

El tiempo de ejecución del postprocesador de BeanDefinitionRegistryPostProcessor BeanFactory que implementa esta interfaz

1. Primero ejecute el postprocesador de BeanFactory que implementa las interfaces de BeanDefinitionRegistryPostProcessor y PriorityOrdered

2. Luego ejecute el postprocesador de BeanFactory que implementa las interfaces BeanDefinitionRegistryPostProcessor y Ordered

3. Finalmente ejecute el postprocesador de BeanFactory que implementa la interfaz de BeanDefinitionRegistryPostProcessor

Tiempo de implementación del postprocesador de BeanFactoryPostProcessor BeanFactory que implementa esta interfaz

4. Primero ejecute el postprocesador de BeanFactory que implementa las interfaces BeanFactoryPostProcessor y PriorityOrdered

5. Luego ejecute el postprocesador de BeanFactory que implementa las interfaces BeanFactoryPostProcessor y Ordered

6. Finalmente ejecute el postprocesador de BeanFactory que implementa la interfaz BeanFactoryPostProcessor

Al ejecutar estos posprocesadores BeanFactory, Spring también ejecutará un posprocesador Bean principalmente para completar la fusión del BeanDefinition padre y el hijo, por lo que el primer punto introducido es muy importante.

ConfigurationClassPostProcessor implementa BeanDefinitionRegistryPostProcessor ¿Qué hace Spring?

Complete el segundo escaneo para analizar todas las anotaciones contenidas en la clase de configuración @Import @PropertySource @ComponentScans @Bean

Y la clase que implementa la interfaz ImportSelector y la interfaz ImportBeanDefinitionRegistrar

Encapsulado en BeanDefinition y registrado en BeanDefinitionMap.

ConfigurationClassPostProcessor implementa el postprocesador BeanFactoryPostProcessor ¿Qué hizo Spring?

Principalmente para completar la mejora de CGLIB para la clase de configuración, veamos lo siguiente

@ComponentScan("org.springframework.test2")
@Configuration
public class AppConfig {
   
   @Bean
   public B b(){
      System.out.println("===b===");
      return new B();
   }

   @Bean
   public  A a(){
      System.out.println("===a===");
      b();
      return new A();
   }

}

¿Por qué la anotación @Configuration solo imprime ayb una vez, pero no b dos veces?

El objeto ay el objeto b son ambos singleton, ¿por qué se inicializan dos veces?

La anotación @Configuration agregada será analizada por la clase ConfigurationClassPostProcessor y se realizará el proxy CGLIB.

Pero, ¿por qué b solo se inicializa una vez después de CGLIB (principio de dependencia cíclica de Spring)?

 registerBeanPostProcessors (beanFactory);

El tiempo de ejecución del postprocesador del BeanPostProcessor Bean que implementa esta interfaz va acompañado del ciclo de vida del Bean.

1. Primero agregue el postprocesador del Bean que implementa las interfaces BeanPostProcessor y PriorityOrdered

2. Agregue el postprocesador del Bean que implementa las interfaces BeanPostProcessor y Ordered

3. Finalmente agregue el postprocesador del Bean que implementa la interfaz BeanPostProcessor

Tiempo de ejecución del postprocesador de Bean

1. Determine si el bean que se está instanciando necesita ser proxy, si es necesario, agréguelo a una colección y devuélvalo vacío

InstantiationAwareBeanPostProcessor # postProcessBeforeInstantiation {return null}

2. Método de construcción inferido

SmartInstantiationAwareBeanPostProcessor # determineCandidateConstructors {return null}

spring-ioc-inferred constructor-manual assembly   spring-ioc-inferred constructor-automatic assembly

3. Fusionar BeanDefinition padre e hijo

MergedBeanDefinitionPostProcessor # postProcessMergedBeanDefinition

4. Dependencia circular, exponer una fábrica y obtener instancias de Bean a través de la fábrica (la razón para exponer la fábrica es ensamblar atributos para el objeto proxy) SmartInstantiationAwareBeanPostProcessor # getEarlyBeanReference

dependencia spring-ioc-cíclica

5. Inyección de atributos, para determinar si el objeto actual permite la inyección de atributos (el valor predeterminado es verdadero) InstantiationAwareBeanPostProcessor # postProcessAfterInstantiation

6. Inyección de atributos inyección manual @Autowired y @Resource inyección automática basada en el mecanismo de reflexión de Java (uno de los modelos de inyección) basado en el mecanismo de introspección de Java

El método de búsqueda de @Autowired y @Resource en el código fuente @Autowired primero busca de acuerdo con el tipo, coloca el tipo encontrado en una colección y luego hace coincidir por nombre en la colección, y viceversa @Resource

Por qué @Autowired y @Resource no son inyección automática, consulte

resorte-ioc-montaje automático

7. Implementar la interfaz Aware e implementar el método Before de BeanPostProcessor por nosotros mismos.

BeanPostProcessor # postProcessBeforeInitialization

8. Proxy Proxy dinámico, y nuestra propia implementación del método After de BeanPostProcessor

BeanPostProcessor # postProcessAfterInitialization

Hay tres formas de ejecutar devoluciones de llamada del ciclo de vida de Bean

Primero, inicialice la devolución de llamada. El orden de ejecución puede existir para los tres tipos. Anotación> Interfaz> xml

El primer <bean init-method = ""> basado en xml

El segundo tipo implementa InitializingBean basado en la interfaz

El tercero se basa en la anotación @PostConstruct

De manera similar, destruye la devolución de llamada

<método-destrucción-frijol = "">  

DestroyBean implementa DisposableBean

@Predestroy

Ejecutar la devolución de llamada del ciclo de vida del contenedor Spring

Clases que implementan la interfaz SmartLifecycle y clases que implementan la interfaz Lifecycle

ciclo de vida de la interfaz {

inicio vacío ();

parada vacía ();

boolean isRunning ();

}

interfaz SmartLifecycle {

isAutoStartup ();

parada void (devolución de llamada ejecutable);

int getPhase ();

}

Hasta ahora, el ciclo de vida de Spring Bean finaliza La inicialización del contenedor Spring está completa.

En resumen, hay dos partes

La primera parte del postprocesador de BeanFactoryPostProcessor BeanFactory completa la mitad de la inicialización del contenedor Spring

La segunda parte del postprocesador BeanPostProcessor Bean completa la otra mitad de la inicialización del contenedor Spring y el ciclo de vida del Bean

Supongo que te gusta

Origin blog.csdn.net/qq_38108719/article/details/103384787
Recomendado
Clasificación