Spring-IOC源码解析

Spring-IOC源码解析

本文我们主要关注下面三点
  • IOC是什么
  • IoC的好处
  • IOC的实现原理

一.IOC是什么

  我们都知道spring的核心技术有AOP和IOC,Ioc(Inversion of Control)
  字面意思即“控制反转”,是一种设计思想而已。最常见的方式被称作依赖注入(Dependency Injection,简称DI),还有一种方式叫“依赖查找”(Dependency Lookup)。
  那么控制反转 是谁控制了谁?又是什么进行了反转呢?
  1:谁控制谁?
      在没有IOC的时候,我们的JAVA程序只能在册程序内部进行依赖对象的创建。IOC运用了IOC容器去创建这些依赖对象的创建,所以是IOC控制了对象,控制了外部依赖的获取
  2:什么反转了呢?
      在没有IOC的时候,我们的JAVA程序只能在对象的内部主动获取依赖对象,而反转是由容器来帮忙创建及注入依赖对象,所以是依赖对象的获取方式反转了,由主动变被动。

二.IoC的好处

  面向对象设计法则之一—— 好莱坞法则:“别找我们,我们找你”
  传统程序都是由我们在类内部主动创建依赖对象,则会导致类类之间高耦合。
  有了IoC容器后,把依赖对象的控制权交给了容器,由容器进行注入,所以对象与对象之间是松散耦合,利于功能复用,更重要的是使得程序的整个结构体系变得灵活。

二.IoC的实现原理

2.1 首先我们介绍一下IOC的核心组件

1.BeanFactory

public interface BeanFactory {

	String FACTORY_BEAN_PREFIX = "&";

	Object getBean(String name) throws BeansException;

	<T> T getBean(String name, Class<T> requiredType) throws BeansException;

	<T> T getBean(Class<T> requiredType) throws BeansException;

	Object getBean(String name, Object... args) throws BeansException;

	<T> T getBean(Class<T> requiredType, Object... args) throws BeansException;

	boolean containsBean(String name);

	boolean isSingleton(String name) throws NoSuchBeanDefinitionException;

	boolean isPrototype(String name) throws NoSuchBeanDefinitionException;

	
	boolean isTypeMatch(String name, ResolvableType typeToMatch) throws NoSuchBeanDefinitionException;

	boolean isTypeMatch(String name, Class<?> typeToMatch) throws NoSuchBeanDefinitionException;

	Class<?> getType(String name) throws NoSuchBeanDefinitionException;

	String[] getAliases(String name);

}

  BeanFactory 是一个最核心最核心的接口,这是IOC容器的接口定义。
  如果IOC是一把枪的话,那么BeanFactory就定义了这把枪的基本功比如枪可以安装子弹,扣动扳机,发射子弹等功能
  SpringBean的创建是典型的工厂模式,在Spring中有许多的IOC容器的实现供用户选择和使用它定义了IOC容器的基本功能,由它的实现类拓展以及进行功能的实现,相互关系如下

在这里插入图片描述

BeanFactory 有三个子类:ListableBeanFactory、HierarchicalBeanFactory 和AutowireCapableBeanFactory。
ListableBeanFactory 接口表示这些 Bean 是可列表的
HierarchicalBeanFactory 表示的是这些 Bean 是有继承关系的
AutowireCapableBeanFactory 接口定义 Bean 的自动装配规则
这四个接口共同定义了 Bean 的集合、Bean 之间的关系、以及 Bean 行为
BeanFactory 最终的默认实现类是 DefaultListableBeanFactory,他实现了所有的接口,其上层各种接口主要是为了区分在 Spring 内部在操作过程中对象的传递和转化过程中,对象的数据访问所做的限制。

2.ApplicationContext

ApplicationContext是Spring提供的一个高级的IoC容器,它基IoC容器的基本功能,另外提供了以下的增强服务。
 1.  支持信息源,可以实现国际化。(实现MessageSource接口)
 2.  访问资源。(实现ResourcePatternResolver接口,这个后面要讲)
 3.  支持应用事件。(实现ApplicationEventPublisher接口)
 
 引用BeanFactory例子 如果IOC是一把枪的话,那么BeanFactory就定义了这把枪的基本功比如枪可以安装子弹,扣动扳机,发射子弹等功能,当然ApplicationContext就是一把更牛X的枪,比如增加了瞄准镜,消音器等功能

3.BeanDefinition

2.2 搭建简单的IOC例子
下面我们搭建一个spirng maven 项目

在这里插入图片描述

userService.java

package com.zes.spring.ioc;

public class UserService {

  public void getUser() {
    System.out.println("query user from DB");
  }
}

application.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
  xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">
  <bean name="userService" class="com.zes.spring.ioc.UserService"></bean>
</beans>

Test.java

package com.zes.spring.ioc;
import org.springframework.context.support.ClassPathXmlApplicationContext;
public class Test {
  
  public static void main(String[] args) {
    ClassPathXmlApplicationContext context = new ClassPathXmlApplicationContext("application.xml");
    UserService userService = (UserService) context.getBean("userService");
    userService.getUser();
  }
}


运行Test.main 可以在控制台中打印 query user from DB
2.3 源码分析

我们通过 ClassPathXmlApplicationContext context = new ClassPathXmlApplicationContext(“application.xml”);
创建了一个容器,就可以用了,那么容器的创建过程是怎么样的,以及我们的UserService是以什么样的身份何时被配置到IOC中的呢?又是如何取出的呢?
我们点进去调用的ClassPathXmlApplicationContext的构造方法看下

 
  public ClassPathXmlApplicationContext(String... configLocations) throws BeansException {
    this(configLocations, true, (ApplicationContext)null);
  }

可以看出构造方法被重载了,可以看到该构造方法被重载了,可以传递 configLocation 数组。
也就是说,可以传递过个配置文件的地址。默认刷新为true,parent 容器为null。进入另一个构造器:


  public ClassPathXmlApplicationContext(String[] configLocations, boolean refresh, @Nullable ApplicationContext parent) throws BeansException {
    super(parent);
    this.setConfigLocations(configLocations);
    if (refresh) {
      this.refresh();
    }

  }

该构造器一是设置配置文件,二是刷新容器,我们不难猜出,refresh 方法才是初始化容器的最关键方法。
我们进入这个方法,这个方法是 ClassPathXmlApplicationContext 的父类AbstractXmlApplicationContext 的父类AbstractRefreshableConfigApplicationContext 的父类AbstractRefreshableApplicationContext的父类AbstractApplicationContext 的方法。


  public void refresh() throws BeansException, IllegalStateException {
    Object var1 = this.startupShutdownMonitor;
    synchronized(this.startupShutdownMonitor) {
        // 为刷新准备应用上下文
      this.prepareRefresh();
       //刷新子类工厂,在子类中refreshBeanFactory()的地方创建bean工厂,根据配置文件生成bean定义
      ConfigurableListableBeanFactory beanFactory = this.obtainFreshBeanFactory();
      // 在这个上下文中使用bean工厂
      this.prepareBeanFactory(beanFactory);

      try {
         // 设置BeanFactory的后置处理器
        postProcessBeanFactory(beanFactory);
        // 调用BeanFactory的后处理器,这些后处理器是在Bean定义中向容器注册的
        invokeBeanFactoryPostProcessors(beanFactory);
        // 注册Bean的后处理器,在Bean创建过程中调用
        registerBeanPostProcessors(beanFactory);
        //对上下文的消息源进行初始化
        initMessageSource();
        // 初始化上下文中的事件机制
        initApplicationEventMulticaster();
        // 初始化其他的特殊Bean
        onRefresh();
        // 检查监听Bean并且将这些Bean向容器注册
        registerListeners();
        // 实例化所有的(non-lazy-init)单件
        finishBeanFactoryInitialization(beanFactory);
        //  发布容器事件,结束refresh过程
                finishRefresh();
      } catch (BeansException var9) {
        if (this.logger.isWarnEnabled()) {
          this.logger.warn("Exception encountered during context initialization - cancelling refresh attempt: " + var9);
        }
        // 异常情况便销毁bean
        this.destroyBeans();
        // 把 this.active.set(false);
        this.cancelRefresh(var9);
        
        throw var9;
      } finally {
        this.resetCommonCaches();
      }

    }
  }

这段代码就是spring IOC初始化的所有逻辑,基本思想逻辑包含五步

image

我们看第一步构建BeanFactory的业务逻辑 this.obtainFreshBeanFactory方法
 protected ConfigurableListableBeanFactory obtainFreshBeanFactory() {
    this.refreshBeanFactory();
    return this.getBeanFactory();
  }
  
  
  这个方法调用了 this.refreshBeanFactory()方法,返回一个ConfigurableListableBeanFactory
  refreshBeanFactory是模板方法由AbstractRefreshableApplicationContext具体实现我们看代码实现
  

  protected final void refreshBeanFactory() throws BeansException {
    if (this.hasBeanFactory()) {
    // 如果已经有就销毁并关闭
      this.destroyBeans();
      this.closeBeanFactory();
    }

    try {
     //创建一个DefaultListableBeanFactory
      DefaultListableBeanFactory beanFactory = this.createBeanFactory();
      //序列化
      beanFactory.setSerializationId(this.getId());
      // 定制的BeanFactory
      this.customizeBeanFactory(beanFactory);
      // 加载bean
      this.loadBeanDefinitions(beanFactory);
      Object var2 = this.beanFactoryMonitor;
      synchronized(this.beanFactoryMonitor) {
        this.beanFactory = beanFactory;
      }
    } catch (IOException var5) {
      throw new ApplicationContextException("I/O error parsing bean definition source for " + this.getDisplayName(), var5);
    }
  }

这里有个很重要的方法, this.loadBeanDefinitions(beanFactory);
可以看出这是加载BeanDefinitions的方法,Definition是bean被包装过后的身份,是ioc中的对象的数据结构。
这个方法也是抽象的,默认实现在AbstractXmlApplicationContext 当中,我们找到对应的代码


  protected void loadBeanDefinitions(DefaultListableBeanFactory beanFactory) throws BeansException, IOException {
    //构造一个 XmlBeanDefinitionReader  用于读取xml文件
    XmlBeanDefinitionReader beanDefinitionReader = new XmlBeanDefinitionReader(beanFactory);
    //设置环境
    beanDefinitionReader.setEnvironment(this.getEnvironment());
    // 设置资源加载器
    beanDefinitionReader.setResourceLoader(this);
    beanDefinitionReader.setEntityResolver(new ResourceEntityResolver(this));
    // 最后两行用于加载BeanDefinitions 
    this.initBeanDefinitionReader(beanDefinitionReader);

    this.loadBeanDefinitions(beanDefinitionReader);
  }

其中loadBeanDefinitions是核心代码,我们看源码


  protected void loadBeanDefinitions(XmlBeanDefinitionReader reader) throws BeansException, IOException {
    // 得到配置文件
    Resource[] configResources = this.getConfigResources();
    if (configResources != null) {
      reader.loadBeanDefinitions(configResources);
    }

    String[] configLocations = this.getConfigLocations();
    if (configLocations != null) {
      reader.loadBeanDefinitions(configLocations);
    }

  }

~~~~~~~~~~~回忆第一步我们在ClassPathXmlApplicationContext的构造方法已经看到,把文件("application.xml")路径塞到了
this.setConfigLocations(configLocations)这个方法。所以这里会略过第一个判断继续执行 遍历configLocations数组。
通过配置文件循环加载BeanDefinitions ,我们继续看loadBeanDefinitions方法。

	@Override
	public int loadBeanDefinitions(String... locations) throws BeanDefinitionStoreException {
		Assert.notNull(locations, "Location array must not be null");
		int count = 0;
		for (String location : locations) {
			count += loadBeanDefinitions(location);
		}
		return count;
	}
	
======================================

 很明显没有我们想看的,继续点进去loadBeanDefinitions方法,进入了AbstractBeanDefinitionReader类的loadBeanDefinitions方法
 
 ====================================
 
 	public int loadBeanDefinitions(String location, @Nullable Set<Resource> actualResources) throws BeanDefinitionStoreException {
 	// 获取到资源加载器
		ResourceLoader resourceLoader = getResourceLoader();
		if (resourceLoader == null) {
			throw new BeanDefinitionStoreException(
					"Cannot load bean definitions from location [" + location + "]: no ResourceLoader available");
		}

		if (resourceLoader instanceof ResourcePatternResolver) {
			// Resource pattern matching available.
			try {
			// 获取到文件资源数组
				Resource[] resources = ((ResourcePatternResolver) resourceLoader).getResources(location);
			    // 加载loadBeanDefinitions
				int count = loadBeanDefinitions(resources);
				if (actualResources != null) {
					Collections.addAll(actualResources, resources);
				}
				if (logger.isTraceEnabled()) {
					logger.trace("Loaded " + count + " bean definitions from location pattern [" + location + "]");
				}
				return count;
			}
			catch (IOException ex) {
				throw new BeanDefinitionStoreException(
						"Could not resolve bean definition resource pattern [" + location + "]", ex);
			}
		}
		else {
			// Can only load single resources by absolute URL.
			Resource resource = resourceLoader.getResource(location);
			int count = loadBeanDefinitions(resource);
			if (actualResources != null) {
				actualResources.add(resource);
			}
			if (logger.isTraceEnabled()) {
				logger.trace("Loaded " + count + " bean definitions from location [" + location + "]");
			}
			return count;
		}
	}
 
 
 ===========继续点loadBeanDefinitions方法进入XmlBeanDefinitionReader类 
 
 public int loadBeanDefinitions(EncodedResource encodedResource) throws BeanDefinitionStoreException {
		Assert.notNull(encodedResource, "EncodedResource must not be null");
		if (logger.isTraceEnabled()) {
			logger.trace("Loading XML bean definitions from " + encodedResource);
		}

		Set<EncodedResource> currentResources = this.resourcesCurrentlyBeingLoaded.get();
		if (currentResources == null) {
			currentResources = new HashSet<>(4);
			this.resourcesCurrentlyBeingLoaded.set(currentResources);
		}
		if (!currentResources.add(encodedResource)) {
			throw new BeanDefinitionStoreException(
					"Detected cyclic loading of " + encodedResource + " - check your import definitions!");
		}
		try {
			InputStream inputStream = encodedResource.getResource().getInputStream();
			try {
				InputSource inputSource = new InputSource(inputStream);
				if (encodedResource.getEncoding() != null) {
					inputSource.setEncoding(encodedResource.getEncoding());
				}
				return doLoadBeanDefinitions(inputSource, encodedResource.getResource());
			}
			finally {
				inputStream.close();
			}
		}
		catch (IOException ex) {
			throw new BeanDefinitionStoreException(
					"IOException parsing XML document from " + encodedResource.getResource(), ex);
		}
		finally {
			currentResources.remove(encodedResource);
			if (currentResources.isEmpty()) {
				this.resourcesCurrentlyBeingLoaded.remove();
			}
		}
	}

 ===========继续点doLoadBeanDefinitions方法
 
 	protected int doLoadBeanDefinitions(InputSource inputSource, Resource resource)
			throws BeanDefinitionStoreException {

		try {
			Document doc = doLoadDocument(inputSource, resource);
			int count = registerBeanDefinitions(doc, resource);
			if (logger.isDebugEnabled()) {
				logger.debug("Loaded " + count + " bean definitions from " + resource);
			}
			return count;
		}
		catch (BeanDefinitionStoreException ex) {
			throw ex;
		}
		catch (SAXParseException ex) {
			throw new XmlBeanDefinitionStoreException(resource.getDescription(),
					"Line " + ex.getLineNumber() + " in XML document from " + resource + " is invalid", ex);
		}
		catch (SAXException ex) {
			throw new XmlBeanDefinitionStoreException(resource.getDescription(),
					"XML document from " + resource + " is invalid", ex);
		}
		catch (ParserConfigurationException ex) {
			throw new BeanDefinitionStoreException(resource.getDescription(),
					"Parser configuration exception parsing XML from " + resource, ex);
		}
		catch (IOException ex) {
			throw new BeanDefinitionStoreException(resource.getDescription(),
					"IOException parsing XML document from " + resource, ex);
		}
		catch (Throwable ex) {
			throw new BeanDefinitionStoreException(resource.getDescription(),
					"Unexpected exception parsing XML document from " + resource, ex);
		}
	}
	
	

该方法主要逻辑是根据输入流加载 Document 文档对象,然后根据得到的文档对象注册到容器

	public int registerBeanDefinitions(Document doc, Resource resource) throws BeanDefinitionStoreException {
		BeanDefinitionDocumentReader documentReader = createBeanDefinitionDocumentReader();
		int countBefore = getRegistry().getBeanDefinitionCount();
		// 核心
		documentReader.registerBeanDefinitions(doc, createReaderContext(resource));
		return getRegistry().getBeanDefinitionCount() - countBefore;
	}

首先创建了一个BeanDefinitionDocumentReader 继续进入registerBeanDefinitions方法

protected void parseBeanDefinitions(Element root, BeanDefinitionParserDelegate delegate) {
		if (delegate.isDefaultNamespace(root)) {
			NodeList nl = root.getChildNodes();
			for (int i = 0; i < nl.getLength(); i++) {
				Node node = nl.item(i);
				if (node instanceof Element) {
					Element ele = (Element) node;
					if (delegate.isDefaultNamespace(ele)) {
						parseDefaultElement(ele, delegate);
					}
					else {
						delegate.parseCustomElement(ele);
					}
				}
			}
		}
		else {
			delegate.parseCustomElement(root);
		}
	}

文档解析 最终调用了parseDefaultElement方法。感觉我们已进入一个无底洞,不急。5分钟抽根烟…继续点进去


	private void parseDefaultElement(Element ele, BeanDefinitionParserDelegate delegate) {
		if (delegate.nodeNameEquals(ele, IMPORT_ELEMENT)) {
			importBeanDefinitionResource(ele);
		}
		else if (delegate.nodeNameEquals(ele, ALIAS_ELEMENT)) {
			processAliasRegistration(ele);
		}
		// BEAN_ELEMENT = "bean"; 
		else if (delegate.nodeNameEquals(ele, BEAN_ELEMENT)) {
			processBeanDefinition(ele, delegate);
		}
		else if (delegate.nodeNameEquals(ele, NESTED_BEANS_ELEMENT)) {
			// recurse
			doRegisterBeanDefinitions(ele);
		}
	}

所以我们继续进入processBeanDefinition方法

	/**
	 * Process the given bean element, parsing the bean definition
	 * and registering it with the registry.
	 */
	protected void processBeanDefinition(Element ele, BeanDefinitionParserDelegate delegate) {
		BeanDefinitionHolder bdHolder = delegate.parseBeanDefinitionElement(ele);
		if (bdHolder != null) {
			bdHolder = delegate.decorateBeanDefinitionIfRequired(ele, bdHolder);
			try {
				// Register the final decorated instance.
				BeanDefinitionReaderUtils.registerBeanDefinition(bdHolder, getReaderContext().getRegistry());
			}
			catch (BeanDefinitionStoreException ex) {
				getReaderContext().error("Failed to register bean definition with name '" +
						bdHolder.getBeanName() + "'", ele, ex);
			}
			// Send registration event.
			getReaderContext().fireComponentRegistered(new BeanComponentDefinition(bdHolder));
		}
	}

首先得到了一个BeanDefinitionHolder,然后调用了BeanDefinitionReaderUtils.registerBeanDefinition 方法
最后

/**
	 * Register the given bean definition with the given bean factory.
	 * @param definitionHolder the bean definition including name and aliases
	 * @param registry the bean factory to register with
	 * @throws BeanDefinitionStoreException if registration failed
	 */
	public static void registerBeanDefinition(
			BeanDefinitionHolder definitionHolder, BeanDefinitionRegistry registry)
			throws BeanDefinitionStoreException {

		// Register bean definition under primary name.
		String beanName = definitionHolder.getBeanName();
		registry.registerBeanDefinition(beanName, definitionHolder.getBeanDefinition());

		// Register aliases for bean name, if any.
		String[] aliases = definitionHolder.getAliases();
		if (aliases != null) {
			for (String alias : aliases) {
				registry.registerAlias(beanName, alias);
			}
		}
	}

从BeanDefinitionHolder拿到beanname 和BeanDefinition 塞入registerBeanDefinition方法

	@Override
	public void registerBeanDefinition(String beanName, BeanDefinition beanDefinition)
			throws BeanDefinitionStoreException {

		Assert.hasText(beanName, "Bean name must not be empty");
		Assert.notNull(beanDefinition, "BeanDefinition must not be null");

		if (beanDefinition instanceof AbstractBeanDefinition) {
			try {
				((AbstractBeanDefinition) beanDefinition).validate();
			}
			catch (BeanDefinitionValidationException ex) {
				throw new BeanDefinitionStoreException(beanDefinition.getResourceDescription(), beanName,
						"Validation of bean definition failed", ex);
			}
		}

		BeanDefinition existingDefinition = this.beanDefinitionMap.get(beanName);
		if (existingDefinition != null) {
			if (!isAllowBeanDefinitionOverriding()) {
				throw new BeanDefinitionOverrideException(beanName, beanDefinition, existingDefinition);
			}
			else if (existingDefinition.getRole() < beanDefinition.getRole()) {
				// e.g. was ROLE_APPLICATION, now overriding with ROLE_SUPPORT or ROLE_INFRASTRUCTURE
				if (logger.isInfoEnabled()) {
					logger.info("Overriding user-defined bean definition for bean '" + beanName +
							"' with a framework-generated bean definition: replacing [" +
							existingDefinition + "] with [" + beanDefinition + "]");
				}
			}
			else if (!beanDefinition.equals(existingDefinition)) {
				if (logger.isDebugEnabled()) {
					logger.debug("Overriding bean definition for bean '" + beanName +
							"' with a different definition: replacing [" + existingDefinition +
							"] with [" + beanDefinition + "]");
				}
			}
			else {
				if (logger.isTraceEnabled()) {
					logger.trace("Overriding bean definition for bean '" + beanName +
							"' with an equivalent definition: replacing [" + existingDefinition +
							"] with [" + beanDefinition + "]");
				}
			}
			//
			
		=====================注意==========================
			
			this.beanDefinitionMap.put(beanName, beanDefinition);
		}
		else {
			if (hasBeanCreationStarted()) {
				// Cannot modify startup-time collection elements anymore (for stable iteration)
				synchronized (this.beanDefinitionMap) {
					this.beanDefinitionMap.put(beanName, beanDefinition);
					List<String> updatedDefinitions = new ArrayList<>(this.beanDefinitionNames.size() + 1);
					updatedDefinitions.addAll(this.beanDefinitionNames);
					updatedDefinitions.add(beanName);
					this.beanDefinitionNames = updatedDefinitions;
					if (this.manualSingletonNames.contains(beanName)) {
						Set<String> updatedSingletons = new LinkedHashSet<>(this.manualSingletonNames);
						updatedSingletons.remove(beanName);
						this.manualSingletonNames = updatedSingletons;
					}
				}
			}
			else {
				// Still in startup registration phase
				this.beanDefinitionMap.put(beanName, beanDefinition);
				this.beanDefinitionNames.add(beanName);
				this.manualSingletonNames.remove(beanName);
			}
			this.frozenBeanDefinitionNames = null;
		}

		if (existingDefinition != null || containsSingleton(beanName)) {
			resetBeanDefinition(beanName);
		}
	}

我们终于走到了最后一步 this.beanDefinitionMap.put(beanName, beanDefinition);

/** Map of bean definition objects, keyed by bean name. */
private final Map<String, BeanDefinition> beanDefinitionMap = new ConcurrentHashMap<>(256);

这个是用来存储bean对象的map
结尾的流程我们知道了 那么beanDefinition我们没有看他的实现逻辑,还记得刚才我抽的那根烟么? 抽完之后我们进入了
processBeanDefinition方法,我们看这句话
BeanDefinitionHolder bdHolder = delegate.parseBeanDefinitionElement(ele);
parseBeanDefinitionElement 干了什么
好吧!!!!
该方法又调用了
AbstractBeanDefinition beanDefinition = parseBeanDefinitionElement(ele, beanName, containingBean);

	/**
	 * Parse the bean definition itself, without regard to name or aliases. May return
	 * {@code null} if problems occurred during the parsing of the bean definition.
	 */
	@Nullable
	public AbstractBeanDefinition parseBeanDefinitionElement(
			Element ele, String beanName, @Nullable BeanDefinition containingBean) {

		this.parseState.push(new BeanEntry(beanName));

		String className = null;
		if (ele.hasAttribute(CLASS_ATTRIBUTE)) {
			className = ele.getAttribute(CLASS_ATTRIBUTE).trim();
		}
		String parent = null;
		if (ele.hasAttribute(PARENT_ATTRIBUTE)) {
			parent = ele.getAttribute(PARENT_ATTRIBUTE);
		}

		try {
			AbstractBeanDefinition bd = createBeanDefinition(className, parent);

			parseBeanDefinitionAttributes(ele, beanName, containingBean, bd);
			bd.setDescription(DomUtils.getChildElementValueByTagName(ele, DESCRIPTION_ELEMENT));

			parseMetaElements(ele, bd);
			parseLookupOverrideSubElements(ele, bd.getMethodOverrides());
			parseReplacedMethodSubElements(ele, bd.getMethodOverrides());

			parseConstructorArgElements(ele, bd);
			parsePropertyElements(ele, bd);
			parseQualifierElements(ele, bd);

			bd.setResource(this.readerContext.getResource());
			bd.setSource(extractSource(ele));

			return bd;
		}
		catch (ClassNotFoundException ex) {
			error("Bean class [" + className + "] not found", ele, ex);
		}
		catch (NoClassDefFoundError err) {
			error("Class that bean class [" + className + "] depends on not found", ele, err);
		}
		catch (Throwable ex) {
			error("Unexpected failure during bean definition parsing", ele, ex);
		}
		finally {
			this.parseState.pop();
		}

		return null;
	}

取出了className 然后createBeanDefinition(className, parent)
最终调用了BeanDefinitionReaderUtils.createBeanDefinition 方法

	/**
	 * Create a bean definition for the given class name and parent name.
	 * @param className the name of the bean class
	 * @param parentName the name of the bean's parent bean
	 * @return the newly created bean definition
	 * @throws ClassNotFoundException if bean class resolution was attempted but failed
	 */
	protected AbstractBeanDefinition createBeanDefinition(@Nullable String className, @Nullable String parentName)
			throws ClassNotFoundException {

		return BeanDefinitionReaderUtils.createBeanDefinition(
				parentName, className, this.readerContext.getBeanClassLoader());
	}

BeanDefinitionReaderUtils.createBeanDefinition如下

	/**
	 * Create a new GenericBeanDefinition for the given parent name and class name,
	 * eagerly loading the bean class if a ClassLoader has been specified.
	 * @param parentName the name of the parent bean, if any
	 * @param className the name of the bean class, if any
	 * @param classLoader the ClassLoader to use for loading bean classes
	 * (can be {@code null} to just register bean classes by name)
	 * @return the bean definition
	 * @throws ClassNotFoundException if the bean class could not be loaded
	 */
	public static AbstractBeanDefinition createBeanDefinition(
			@Nullable String parentName, @Nullable String className, @Nullable ClassLoader classLoader) throws ClassNotFoundException {

		GenericBeanDefinition bd = new GenericBeanDefinition();
		bd.setParentName(parentName);
		if (className != null) {
			if (classLoader != null) {
				bd.setBeanClass(ClassUtils.forName(className, classLoader));
			}
			else {
				bd.setBeanClassName(className);
			}
		}
		return bd;
	}

	/

GenericBeanDefinition继承了AbstractBeanDefinition 。class类信息放进去就结束了

此时我们的bean工厂构造完成,以及bean信息也定义好了,还没有进行bean的实例化

在我们分析源码的开始refresh()中 有一步骤为

finishBeanFactoryInitialization(beanFactory);
这个方法有一步骤beanFactory.preInstantiateSingletons()最为关键


    public void preInstantiateSingletons() throws BeansException {
        if (this.logger.isDebugEnabled()) {
            this.logger.debug("Pre-instantiating singletons in " + this);
        }

        // Iterate over a copy to allow for init methods which in turn register new bean definitions.
        // While this may not be part of the regular factory bootstrap, it does otherwise work fine.
        // 首先将bean difinition放到一个新的集合中。
        List<String> beanNames = new ArrayList<String>(this.beanDefinitionNames);

        // Trigger initialization of all non-lazy singleton beans...
        //遍历
        for (String beanName : beanNames) {
            RootBeanDefinition bd = getMergedLocalBeanDefinition(beanName);

            if (!bd.isAbstract() && bd.isSingleton() && !bd.isLazyInit()) {
               //是否为FactoryBean,不是的话直接实例化
                if (isFactoryBean(beanName)) {
                    final FactoryBean<?> factory = (FactoryBean<?>) getBean(FACTORY_BEAN_PREFIX + beanName);
                    boolean isEagerInit;
                    if (System.getSecurityManager() != null && factory instanceof SmartFactoryBean) {
                        isEagerInit = AccessController.doPrivileged(new PrivilegedAction<Boolean>() {
                            @Override
                            public Boolean run() {
                                return ((SmartFactoryBean<?>) factory).isEagerInit();
                            }
                        }, getAccessControlContext());
                    }
                      // 如果是FactoryBean,判断FactoryBean有没有其他的的配置
                    else {
                        isEagerInit = (factory instanceof SmartFactoryBean &&
                                ((SmartFactoryBean<?>) factory).isEagerInit());
                    }
                    if (isEagerInit) {
                        getBean(beanName);
                    }
                }
                else {
                    getBean(beanName);
                }
            }
        }

        // Trigger post-initialization callback for all applicable beans...
        // 触发所有应用Bean的post-initialization 回调
        for (String beanName : beanNames) {
           //获取Bean的实例
            Object singletonInstance = getSingleton(beanName);
            // 如果实例实现了SmartInitializingSingleton,执行afterSingletonsInstantiated方法。
            if (singletonInstance instanceof SmartInitializingSingleton) {
                final SmartInitializingSingleton smartSingleton = (SmartInitializingSingleton) singletonInstance;
                if (System.getSecurityManager() != null) {
                    AccessController.doPrivileged(new PrivilegedAction<Object>() {
                        @Override
                        public Object run() {
                            smartSingleton.afterSingletonsInstantiated();
                            return null;
                        }
                    }, getAccessControlContext());
                }
                else {
                    smartSingleton.afterSingletonsInstantiated();
                }
            }
        }
    }

getBean -> doGetBean

protected <T> T doGetBean(String name, Class<T> requiredType, final Object[] args, boolean typeCheckOnly) throws BeansException {
        final String beanName = this.transformedBeanName(name);//解析beanName 因为如果是FactoryBean会带上&符号
        Object sharedInstance = this.getSingleton(beanName);//尝试从缓存中获取单例bean
        Object bean;
        if(sharedInstance != null && args == null) {//如果已经存在
            ·····
            bean = this.getObjectForBeanInstance(sharedInstance, name, beanName, (RootBeanDefinition)null);//主要是对FactoryBean进行处理
        } else {
            BeanFactory ex = this.getParentBeanFactory();
            if(ex != null && !this.containsBeanDefinition(beanName)) {//父bean工厂进行生产
                String var24 = this.originalBeanName(name);
                if(args != null) {
                    return ex.getBean(var24, args);
                }

                return ex.getBean(var24, requiredType);
            }

            if(!typeCheckOnly) {
                this.markBeanAsCreated(beanName);//把bean添加到标识准备好创建的list
            }

            try {
                final RootBeanDefinition ex1 = this.getMergedLocalBeanDefinition(beanName);// 生成简单beanDefintion
                this.checkMergedBeanDefinition(ex1, beanName, args);
                String[] dependsOn = ex1.getDependsOn();//获取它的依赖bean
                String[] scopeName;
                if(dependsOn != null) {
                    scopeName = dependsOn;
                    int scope = dependsOn.length;

                    for(int ex2 = 0; ex2 < scope; ++ex2) {//循环生产所依赖的bean
                        String dependsOnBean = scopeName[ex2];
                        this.getBean(dependsOnBean);
                        this.registerDependentBean(dependsOnBean, beanName);//注册到依赖bean集合
                    }
                }

                if(ex1.isSingleton()) {//判断是否单例
                    sharedInstance = this.getSingleton(beanName, new ObjectFactory() {
                        public Object getObject() throws BeansException {
                            try {
                                return AbstractBeanFactory.this.createBean(beanName, ex1, args);//真正生成bean的方法,这里会对循环依赖问题进行处理
                            } catch (BeansException var2) {
                                AbstractBeanFactory.this.destroySingleton(beanName);
                                throw var2;
                            }
                        }
                    });
                    bean = this.getObjectForBeanInstance(sharedInstance, name, beanName, ex1);
                } else if(ex1.isPrototype()) {
                    scopeName = null;

                    Object var25;
                    try {
                        this.beforePrototypeCreation(beanName);
                        var25 = this.createBean(beanName, ex1, args);
                    } finally {
                        this.afterPrototypeCreation(beanName);
                    }

                    bean = this.getObjectForBeanInstance(var25, name, beanName, ex1);
                } else {
                    String var26 = ex1.getScope();
                    Scope var27 = (Scope)this.scopes.get(var26);
                    if(var27 == null) {
                        throw new IllegalStateException("No Scope registered for scope \'" + var26 + "\'");
                    }

                    try {
                        Object var28 = var27.get(beanName, new ObjectFactory() {
                            public Object getObject() throws BeansException {
                                AbstractBeanFactory.this.beforePrototypeCreation(beanName);

                                Object var1;
                                try {
                                    var1 = AbstractBeanFactory.this.createBean(beanName, ex1, args);
                                } finally {
                                    AbstractBeanFactory.this.afterPrototypeCreation(beanName);
                                }

                                return var1;
                            }
                        });
                        bean = this.getObjectForBeanInstance(var28, name, beanName, ex1);
                    } catch (IllegalStateException var21) {
                        throw new BeanCreationException(beanName, "Scope \'" + var26 + "\' is not active for the current thread; " + "consider defining a scoped proxy for this bean if you intend to refer to it from a singleton", var21);
                    }
                }
            } catch (BeansException var23) {
                this.cleanupAfterBeanCreationFailure(beanName);
                throw var23;
            }
        }

        if(requiredType != null && bean != null && !requiredType.isAssignableFrom(bean.getClass())) {
            try {
                return this.getTypeConverter().convertIfNecessary(bean, requiredType);
            } catch (TypeMismatchException var22) {
                if(this.logger.isDebugEnabled()) {
                    this.logger.debug("Failed to convert bean \'" + name + "\' to required type [" + ClassUtils.getQualifiedName(requiredType) + "]", var22);
                }

                throw new BeanNotOfRequiredTypeException(name, requiredType, bean.getClass());
            }
        } else {
            return bean;
        }
    }
===
   public Object getSingleton(String beanName, ObjectFactory singletonFactory) {
       Map var3 = this.singletonObjects;
       synchronized(this.singletonObjects) {
           Object singletonObject = this.singletonObjects.get(beanName);
           if(singletonObject == null) {
               ···
               try {
                   singletonObject = singletonFactory.getObject();//获取bean
               } catch (BeanCreationException var14) {
                   BeanCreationException ex = var14;
                   if(recordSuppressedExceptions) {
                       Iterator i$ = this.suppressedExceptions.iterator();

                       while(i$.hasNext()) {
                           Exception suppressedException = (Exception)i$.next();
                           ex.addRelatedCause(suppressedException);
                       }
                   }

                   throw ex;
               } finally {
                   if(recordSuppressedExceptions) {
                       this.suppressedExceptions = null;
                   }
               }

               this.addSingleton(beanName, singletonObject);//添加到单例缓存map
           }

           return singletonObject != NULL_OBJECT?singletonObject:null;
       }
   }
 

==

```
protected Object createBean(String beanName, RootBeanDefinition mbd, Object[] args) throws BeanCreationException {
    this.resolveBeanClass(mbd, beanName, new Class[0]);

    try {
        mbd.prepareMethodOverrides();
    } catch (BeanDefinitionValidationException var5) {
        throw new BeanDefinitionStoreException(mbd.getResourceDescription(), beanName, "Validation of method overrides failed", var5);
    }

    Object beanInstance;
    try {
        beanInstance = this.resolveBeforeInstantiation(beanName, mbd);//开始初始化工作
        if(beanInstance != null) {
            return beanInstance;
        }
    } catch (Throwable var6) {
        throw new BeanCreationException(mbd.getResourceDescription(), beanName, "BeanPostProcessor before instantiation of bean failed", var6);
    }

    beanInstance = this.doCreateBean(beanName, mbd, args);//生产bean
    if(this.logger.isDebugEnabled()) {
        this.logger.debug("Finished creating instance of bean \'" + beanName + "\'");
    }

    return beanInstance;
}




protected Object resolveBeforeInstantiation(String beanName, RootBeanDefinition mbd) {
    Object bean = null;
    if(!Boolean.FALSE.equals(mbd.beforeInstantiationResolved)) {
        if(mbd.hasBeanClass() && !mbd.isSynthetic() && this.hasInstantiationAwareBeanPostProcessors()) {
            bean = this.applyBeanPostProcessorsBeforeInstantiation(mbd.getBeanClass(), beanName);//对实现InstantiationAwareBeanPostProcessor接口的bean进行初始化
            if(bean != null) {
                bean = this.applyBeanPostProcessorsAfterInitialization(bean, beanName);//执行beanPostProcessor的AfterInitialization方法 
            }
        }

        mbd.beforeInstantiationResolved = Boolean.valueOf(bean != null);
    }

    return bean;
}



protected Object doCreateBean(final String beanName, final RootBeanDefinition mbd, Object[] args) {
    BeanWrapper instanceWrapper = null;
    if(mbd.isSingleton()) {
        instanceWrapper = (BeanWrapper)this.factoryBeanInstanceCache.remove(beanName);
    }

    if(instanceWrapper == null) {
        instanceWrapper = this.createBeanInstance(beanName, mbd, args);
    }

    final Object bean = instanceWrapper != null?instanceWrapper.getWrappedInstance():null;
    Class beanType = instanceWrapper != null?instanceWrapper.getWrappedClass():null;
    Object earlySingletonExposure = mbd.postProcessingLock;
    synchronized(mbd.postProcessingLock) {
        if(!mbd.postProcessed) {
            this.applyMergedBeanDefinitionPostProcessors(mbd, beanType, beanName);//对实现MergedBeanDefinitionPostProcessor接口的bean进行处理
            mbd.postProcessed = true;
        }
    }

    boolean var19 = mbd.isSingleton() && this.allowCircularReferences && this.isSingletonCurrentlyInCreation(beanName);
    if(var19) {
        if(this.logger.isDebugEnabled()) {
            this.logger.debug("Eagerly caching bean \'" + beanName + "\' to allow for resolving potential circular references");
        }

        this.addSingletonFactory(beanName, new ObjectFactory() {
            public Object getObject() throws BeansException {
                return AbstractAutowireCapableBeanFactory.this.getEarlyBeanReference(beanName, mbd, bean);
            }
        });
    }

    Object exposedObject = bean;

    try {
        this.populateBean(beanName, mbd, instanceWrapper);//设置属性
        if(exposedObject != null) {
            exposedObject = this.initializeBean(beanName, exposedObject, mbd);//初始化bean 先执行BeanPostProcessor的BeforeInitialization方法 然后如果这个bean实现了InitializingBean接口则执行afterPropertiesSet方法  然后执行init-method方法 最后执行BeanPostProcessor的AfterInitialization方法
        }
    } catch (Throwable var17) {
        if(var17 instanceof BeanCreationException && beanName.equals(((BeanCreationException)var17).getBeanName())) {
            throw (BeanCreationException)var17;
        }

        throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Initialization of bean failed", var17);
    }

    if(var19) {
        Object ex = this.getSingleton(beanName, false);
        if(ex != null) {
            if(exposedObject == bean) {
                exposedObject = ex;
            } else if(!this.allowRawInjectionDespiteWrapping && this.hasDependentBean(beanName)) {
                String[] dependentBeans = this.getDependentBeans(beanName);
                LinkedHashSet actualDependentBeans = new LinkedHashSet(dependentBeans.length);
                String[] arr$ = dependentBeans;
                int len$ = dependentBeans.length;

                for(int i$ = 0; i$ < len$; ++i$) {
                    String dependentBean = arr$[i$];
                    if(!this.removeSingletonIfCreatedForTypeCheckOnly(dependentBean)) {
                        actualDependentBeans.add(dependentBean);
                    }
                }

                if(!actualDependentBeans.isEmpty()) {
                    throw new BeanCurrentlyInCreationException(beanName, "Bean with name \'" + beanName + "\' has been injected into other beans [" + StringUtils.collectionToCommaDelimitedString(actualDependentBeans) + "] in its raw version as part of a circular reference, but has eventually been " + "wrapped. This means that said other beans do not use the final version of the " + "bean. This is often the result of over-eager type matching - consider using " + "\'getBeanNamesOfType\' with the \'allowEagerInit\' flag turned off, for example.");
                }
            }
        }
    }

    try {
        this.registerDisposableBeanIfNecessary(beanName, bean, mbd);
        return exposedObject;
    } catch (BeanDefinitionValidationException var16) {
        throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Invalid destruction signature", var16);
    }
}
```

end

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值