SpringIOC源码解析

xiaoxiao2021-02-28  19

透彻理解SpringIOC设计原理分析

接下来我们带着问题学习

1、  Spring平台组成技术体系有哪些?

2、  SpringIoc容器技术的设计演化?

3、  高级形式容器技术ApplicationContext的初始化细节?

4、  容器中的Bean组件如何装配依赖?

 

Spring平台组成技术体系有哪些?

Spring是一个分层框架,由七个体系模块组成。所有的模块都是构建在容器技术上

由上图看出所有的模块都是以SpringCore即Bean容器技术为基础的,换句话说:

SpringIOC容器技术,为我们上层所有模块提供依赖注入,这样上层模块才能正确执行, Java尿性,解耦

SpringIOC都是以面向接口编程, 将IOC容器技术体系勾勒的非常清晰, 实现非常复杂, 子类实现多样性。

容器技术最开始思路?

         BeanFactory:完成Bean实例的提供工作,输入参数,产出成品, 可以反复提供

         BeanFactory源码分析?

        

只需要把FileSystemXmlApplicationContext里面的设计运转原理搞懂就窥视我们Ioc容器的体系

public FileSystemXmlApplicationContext(String[]configLocations, boolean refresh, ApplicationContext parent)      throws BeansException{   // 调用父类的构造, 确认关系   super(parent);   setConfigLocations(configLocations);   if (refresh){      refresh();   }}

refresh方法是主方法

public void refresh() throws BeansException, IllegalStateException {    synchronized (this.startupShutdownMonitor) {       // Prepare this context for refreshing.       prepareRefresh();       // 初始化beanFactory       ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory();       // Prepare the bean factory for use in this context.       prepareBeanFactory(beanFactory);       try {          // Allows post-processing of the bean factory in context subclasses.          postProcessBeanFactory(beanFactory);          // Invoke factory processors registered as beans in the context.          invokeBeanFactoryPostProcessors(beanFactory);          // Register bean processors that intercept bean creation.          registerBeanPostProcessors(beanFactory);          // Initialize message source for this context.          initMessageSource();          // Initialize event multicaster for this context.          initApplicationEventMulticaster();          // Initialize other special beans in specific context subclasses.          onRefresh();          // Check for listener beans and register them.          registerListeners();          // Instantiate all remaining (non-lazy-init) singletons.          finishBeanFactoryInitialization(beanFactory);          // Last step: publish corresponding event.          finishRefresh();       }       catch (BeansException ex) {          // Destroy already created singletons to avoid dangling resources.          destroyBeans();          // Reset 'active' flag.          cancelRefresh(ex);          // Propagate exception to caller.          throw ex;       }    } }

 

@Override protected final void refreshBeanFactory() throws BeansException { // 如果过旧的bean工厂,销毁清空    if (hasBeanFactory()) {       destroyBeans();       closeBeanFactory();    }    try {       DefaultListableBeanFactory beanFactory = createBeanFactory();       beanFactory.setSerializationId(getId());       customizeBeanFactory(beanFactory); // 加载我们外部配置的BeanDefinitions字节信息到工厂       loadBeanDefinitions(beanFactory);       synchronized (this.beanFactoryMonitor) {          this.beanFactory = beanFactory;       }    }    catch (IOException ex) {       throw new ApplicationContextException("I/O error parsing bean definition source for " + getDisplayName(), ex);    } }

再进入 AbstractXmlApplicationContext类中的这个方法;这里加入了reader读取器

@Override protected void loadBeanDefinitions(DefaultListableBeanFactory beanFactory) throws BeansException, IOException {    // 加载xml的读取器到beanFactory中    XmlBeanDefinitionReader beanDefinitionReader = new XmlBeanDefinitionReader(beanFactory);    // Configure the bean definition reader with this context's    // resource loading environment.    beanDefinitionReader.setResourceLoader(this);    beanDefinitionReader.setEntityResolver(new ResourceEntityResolver(this));    // Allow a subclass to provide custom initialization of the reader,    // then proceed with actually loading the bean definitions.    initBeanDefinitionReader(beanDefinitionReader);         // 关键对BeanDefinition进入载入IOC源码分析, 通过Resouce定位路径来读取    loadBeanDefinitions(beanDefinitionReader); }

ResourceLoader如下

   /** Pseudo URL prefix for loading from the class path: "classpath:" */    String CLASSPATH_URL_PREFIX = ResourceUtils.CLASSPATH_URL_PREFIX;

 

获取资源的方法,Resource可以是下面成千上万种子类, IO定位的对象

通过Reader读取器, 通过Resouce(IO)通道来读取外界配置的beanDefinition的信息applicationContext

然后注册到某个集合容器,String Name(bean  id =”xxx”)装配输出这个实例

@Override protected Resource getResourceByPath(String path) {    if (path != null && path.startsWith("/")) {       path = path.substring(1);    }    return new FileSystemResource(path); }

 

Reader的入口,就是在Resource 的基础上来进行加载, 再进入源码分析

Definition? IOC的内部数据结构.

 

注册环节:

BeanDefinitionRegistery

void registerBeanDefinition(String beanName, BeanDefinition beanDefinition)       throws BeanDefinitionStoreException;

ApplicationContext.getBean()扫描注解的时候拿到我们需要的实例, getBean 内部隐化

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

转载请注明原文地址: https://www.6miu.com/read-2300255.html

最新回复(0)