概述
对于Java开发者来说,Spring是我们最熟悉的框架之一,Spring可以说贯穿了Java开发的方方面面,那么我们有理由对Spring实现的过程和思想进行学习,Spring的核心就是IOC和AOP,本次课程我们会从源码角度剖析SpringIOC的实现过程。
Spring的架构
在解析源码之前,我们先对Spring的架构再进行认识:
Spring有很多模块涉及Java开发的各个部分,比如数据库的DAO、ORM以及Web开发、MVC等,所有的模块都是基于SpringCore核心的,Spring的核心就是一个JavaBean的容器,它通过工厂模式,为其它所有子模块提供IOC的服务。
IOC概念
那么什么是IOC呢?IOC就是控制反转(Inverse Of Control),它是面向对象编程的一种设计原则,目的是为了降低对象之间的耦合性,它还有一个好记的名字:依赖注入(DI)。
那么降低对象之间的耦合性真的有那么重要吗?
举个例子:假设人需要开车
class Person{
private Car car = new Car();
public void drive(){
...
}
}
我们在人类中创建了一个汽车类对象,那么人对象就依赖了汽车对象,人上班下班买菜都需要使用汽车,一旦汽车发生了问题,人的方法也都会受影响,不光如此,上面的代码中,人类创建了一个汽车对象,这就意味着,人不光要做自己的事情,还要关注如何制造一辆汽车,这显然是不合逻辑的。
理想的情况是,人不需要关注如何创建汽车,需要汽车时,汽车通过外部机构(如:租车公司)交到人的手里,这样人只需要关注自己的业务逻辑了。
Java项目中有几千个类,可以想象如果我们要自己管理对象之间的依赖关系,以及如何创建这些对象会有多么复杂,所以IOC就出现了。
IOC的原理其实很简单,其实就是通过反射机制调用set方法,将对象注入到对应的属性中。
class Person{
private Car car;
public void setCar(Car car){
this.car = car;
}
...
}
Class personClass = Class.forName("test.Person");
Object person = personClass.newInstance();
Class carClass = Class.forName("test.Car");
Object car = carClass.newInstance();
Method setCar = personClass.getMethod("setCar",Car.class);
setCar.invoke(person,car);
public static void main(String[] args) {
ApplicationContext context = new ClassPathXmlApplicationContext("classpath:applicationContext.xml");
Person person = context.getBean("person",Person.class);
}
IOC实现原理
那么Spring的IOC是如何实现的呢?
其实底层也是反射机制,当然Spring的作者Jason Robin等大牛,为了提高Spring的稳定性、扩展性和性能,对代码进行了大量的封装和优化,这样Spring的代码也越来越复杂。要搞清楚这个过程,我们先了解一些核心API。
Spring的IOC基于工厂模式,它是IOC的容器,为开发者管理对象提供服务。
BeanFactory接口有三个子接口:
- ListableBeanFactory可列举的BeanFactory,也就是可以对里面的Bean进行查找
- HierarchicalBeanFacotry是保存有继承关系的Bean
- AutowireCapableBeanFactory是存在自动转配规则的Bean。
这些接口下面有各种子类,最下面是DefaultListableBeanFactory类,也就是说该类实现了大部分上面接口的功能,是最强的工厂,在IOC中起到重要的作用。
ApplicationContext是应用程序上下文,它也继承了BeanFactory的子接口,可以说是一种更高级的工厂。
比BeanFactory高级的地方有:
1)支持国际化
2)支持资源访问
3)支持事件发布
它是进行依赖注入的入口,常见的子类有:ClassPathXmlApplicationContext、AnnotationConfigApplicationContext、FileSystemApplicationContext。
源码解析
我们将以ClassPathXmlApplicationContext类为入口,解析IOC的源码。
这里有个重要的接口:BeanDefinition,它保存了Bean的各种信息,从XML中解析出来的Bean的信息都封装到BeanDefinition中。
开始解析源码:
ClassPathXmlApplicationContext的几个构造方法,都是最后调用了这个:
public ClassPathXmlApplicationContext(String[] configLocations, boolean refresh, ApplicationContext parent) throws BeansException {
//将父类对象的上下文环境合并到当前对象的环境中
super(parent);
//设置配置文件列表
this.setConfigLocations(configLocations);
if (refresh) {
//核心方法
this.refresh();
}
}
refresh方法是我们分析的核心,它包括XML配置文件的解析,Bean的注册等,定义在AbstractApplicationContext类中。
public void refresh() throws BeansException, IllegalStateException {
Object var1 = this.startupShutdownMonitor;
//同步块,包装下面的操作时同步执行的
synchronized(this.startupShutdownMonitor) {
//进行一些准备工作,记录开始时间,设置启动状态,校验XML等
this.prepareRefresh();
//关键方法,完成了XML的解析和Bean的注册
ConfigurableListableBeanFactory beanFactory = this.obtainFreshBeanFactory();
//为工厂配置类加载器,事件处理器等
this.prepareBeanFactory(beanFactory);
try {
//配置后置处理器,完成一些初始化工作,如果Bean实现了BeanFactoryPostProcessor
//接口,当加载注册完成后还会调用postProcessBeanFactory方法
this.postProcessBeanFactory(beanFactory);
//调用后置处理器的方法
this.invokeBeanFactoryPostProcessors(beanFactory);
//注册后置处理器
this.registerBeanPostProcessors(beanFactory);
//初始化国际化
this.initMessageSource();
//初始化事件广播
this.initApplicationEventMulticaster();
//钩子方法,初始化某些特殊Bean
this.onRefresh();
//注册监听器
this.registerListeners();
//初始化非Lazy-Load的单例Bean
this.finishBeanFactoryInitialization(beanFactory);
//广播事件,刷新完成
this.finishRefresh();
} catch (BeansException var9) {
if (this.logger.isWarnEnabled()) {
this.logger.warn("Exception encountered during context initialization - cancelling refresh attempt: " + var9);
}
this.destroyBeans();
this.cancelRefresh(var9);
throw var9;
} finally {
this.resetCommonCaches();
}
}
}
接下来我们来看核心方法obtainFreshBeanFactory:
protected ConfigurableListableBeanFactory obtainFreshBeanFactory() {
//如果有旧BeanFactory存在,销毁旧的,创建新的
this.refreshBeanFactory();
//获得创建的BeanFactory
ConfigurableListableBeanFactory beanFactory = this.getBeanFactory();
if (this.logger.isDebugEnabled()) {
this.logger.debug("Bean factory for " + this.getDisplayName() + ": " + beanFactory);
}
return beanFactory;
}
进入refreshBeanFactory方法,在AbstractRefreshableApplicationContext类中
protected final void refreshBeanFactory() throws BeansException {
//如果存在BeanFactory实例
if (this.hasBeanFactory()) {
//销毁所有的Bean
this.destroyBeans();
//关闭旧的BeanFactory
this.closeBeanFactory();
}
try {
//创建了一个BeanFacotry,前面介绍过DefaultListableBeanFactory继承和实现了
//BeanFacotry下面大部分的接口和类,是最强大的BeanFactory
DefaultListableBeanFactory beanFactory = this.createBeanFactory();
//设置一个序列化id
beanFactory.setSerializationId(this.getId());
//自定义BeanFacotry,配置是否允许循环引用,Bean覆盖
this.customizeBeanFactory(beanFactory);
//***重点***,加载BeanDefinition
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);
}
}
后面我们重点看Bean是如何加载的,前面我们提到过,Bean的信息被封装到BeanDefinition中,该接口定义了是否单例、是否懒加载、类的父类、类的依赖类、类名等。
看loadBeanDefinitions方法,回到AbstractXmlApplicationContext类:
protected void loadBeanDefinitions(DefaultListableBeanFactory beanFactory) throws BeansException, IOException {
//创建XmlBeanDefinitionReader 对象
XmlBeanDefinitionReader beanDefinitionReader = new XmlBeanDefinitionReader(beanFactory);
//配置XmlBeanDefinitionReader
beanDefinitionReader.setEnvironment(this.getEnvironment());
beanDefinitionReader.setResourceLoader(this);
beanDefinitionReader.setEntityResolver(new ResourceEntityResolver(this));
//初始化XmlBeanDefinitionReader
this.initBeanDefinitionReader(beanDefinitionReader);
//重点,加载BeanDefinition
this.loadBeanDefinitions(beanDefinitionReader);
}
跟进去,还是在这个类里面:
protected void loadBeanDefinitions(XmlBeanDefinitionReader reader) throws BeansException, IOException {
//通过配置资源加载BeanDefinition
Resource[] configResources = this.getConfigResources();
if (configResources != null) {
reader.loadBeanDefinitions(configResources);
}
//通过配置定位加载BeanDefinition
String[] configLocations = this.getConfigLocations();
if (configLocations != null) {
reader.loadBeanDefinitions(configLocations);
}
}
该方法的的实现在AbstractBeanDefinitionReader中
public int loadBeanDefinitions(Resource... resources) throws BeanDefinitionStoreException {
Assert.notNull(resources, "Resource array must not be null");
int counter = 0;
Resource[] var3 = resources;
int var4 = resources.length;
for(int var5 = 0; var5 < var4; ++var5) {
Resource resource = var3[var5];
counter += this.loadBeanDefinitions((Resource)resource);
}
return counter;
}
在XmlBeanDefinitionReader类中
public int loadBeanDefinitions(Resource resource) throws BeanDefinitionStoreException {
return this.loadBeanDefinitions(new EncodedResource(resource));
}
public int loadBeanDefinitions(EncodedResource encodedResource) throws BeanDefinitionStoreException {
Assert.notNull(encodedResource, "EncodedResource must not be null");
if (this.logger.isInfoEnabled()) {
this.logger.info("Loading XML bean definitions from " + encodedResource.getResource());
}
Set<EncodedResource> currentResources = (Set)this.resourcesCurrentlyBeingLoaded.get();
if (currentResources == null) {
currentResources = new HashSet(4);
this.resourcesCurrentlyBeingLoaded.set(currentResources);
}
if (!((Set)currentResources).add(encodedResource)) {
throw new BeanDefinitionStoreException("Detected cyclic loading of " + encodedResource + " - check your import definitions!");
} else {
int var5;
try {
InputStream inputStream = encodedResource.getResource().getInputStream();
try {
InputSource inputSource = new InputSource(inputStream);
if (encodedResource.getEncoding() != null) {
inputSource.setEncoding(encodedResource.getEncoding());
}
//在这里准备加载BeanDefinition了
var5 = this.doLoadBeanDefinitions(inputSource, encodedResource.getResource());
} finally {
inputStream.close();
}
} catch (IOException var15) {
throw new BeanDefinitionStoreException("IOException parsing XML document from " + encodedResource.getResource(), var15);
} finally {
((Set)currentResources).remove(encodedResource);
if (((Set)currentResources).isEmpty()) {
this.resourcesCurrentlyBeingLoaded.remove();
}
}
return var5;
}
}
下面这里是解析XML加载Bean的方法
protected int doLoadBeanDefinitions(InputSource inputSource, Resource resource) throws BeanDefinitionStoreException {
try {
//这里是获得XML文档
Document doc = this.doLoadDocument(inputSource, resource);
//这个方法是加载和注册BeanDefinition
return this.registerBeanDefinitions(doc, resource);
} catch (BeanDefinitionStoreException var4) {
throw var4;
} catch (SAXParseException var5) {
throw new XmlBeanDefinitionStoreException(resource.getDescription(), "Line " + var5.getLineNumber() + " in XML document from " + resource + " is invalid", var5);
} catch (SAXException var6) {
throw new XmlBeanDefinitionStoreException(resource.getDescription(), "XML document from " + resource + " is invalid", var6);
} catch (ParserConfigurationException var7) {
throw new BeanDefinitionStoreException(resource.getDescription(), "Parser configuration exception parsing XML from " + resource, var7);
} catch (IOException var8) {
throw new BeanDefinitionStoreException(resource.getDescription(), "IOException parsing XML document from " + resource, var8);
} catch (Throwable var9) {
throw new BeanDefinitionStoreException(resource.getDescription(), "Unexpected exception parsing XML document from " + resource, var9);
}
}
看这个方法:
public int registerBeanDefinitions(Document doc, Resource resource) throws BeanDefinitionStoreException {
//获得一个读取器
BeanDefinitionDocumentReader documentReader = this.createBeanDefinitionDocumentReader();
//获得之前的BeanDefinition数量
int countBefore = this.getRegistry().getBeanDefinitionCount();
//主要看这里的解析和注册
documentReader.registerBeanDefinitions(doc, this.createReaderContext(resource));
//返回总数量-之前的数量就是现在注册的Bean数量
return this.getRegistry().getBeanDefinitionCount() - countBefore;
}
现在到了DefaultBeanDefinitionDocumentReader类中,实现了BeanDefinitionDocumentReader接口
public void registerBeanDefinitions(Document doc, XmlReaderContext readerContext) {
//获得读取XML的上下文
this.readerContext = readerContext;
this.logger.debug("Loading bean definitions");
//获得XML的根
Element root = doc.getDocumentElement();
//开始解析XML
this.doRegisterBeanDefinitions(root);
}
终于开始真正解析XML了,这个方法从根节点开始一层一层向下解析:
protected void doRegisterBeanDefinitions(Element root) {
//这里是一个委托,而且是父委托,为什么要这样做呢?因为XML的解析是从Beans开始的,但是Beans的上层可能还有Beans,这里是递归往上找到最上层的Beans节点。
BeanDefinitionParserDelegate parent = this.delegate;
this.delegate = this.createDelegate(this.getReaderContext(), root, parent);
if (this.delegate.isDefaultNamespace(root)) {
//这里是解析profile属性,profile属性是Beans的,可以根据不同的环境选择不同的配置
String profileSpec = root.getAttribute("profile");
if (StringUtils.hasText(profileSpec)) {
String[] specifiedProfiles = StringUtils.tokenizeToStringArray(profileSpec, ",; ");
if (!this.getReaderContext().getEnvironment().acceptsProfiles(specifiedProfiles)) {
if (this.logger.isInfoEnabled()) {
this.logger.info("Skipped XML bean definition file due to specified profiles [" + profileSpec + "] not matching: " + this.getReaderContext().getResource());
}
return;
}
}
}
//钩子方法,前置处理
this.preProcessXml(root);
//核心解析方法
this.parseBeanDefinitions(root, this.delegate);
//钩子方法,后置处理
this.postProcessXml(root);
this.delegate = parent;
}
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)) {
//解析默认元素
this.parseDefaultElement(ele, delegate);
} else {
//解析自定义元素
delegate.parseCustomElement(ele);
}
}
}
} else {
delegate.parseCustomElement(root);
}
}
上面方法中会判断节点是否是默认命名空间,如果是默认的就解析默认的元素,如果不是就解析自定义元素,这里我们关键要弄清楚什么是默认的命名空间?默认的元素有哪些?哪些又是自定义元素?
这些问题,我们要了解Spring的配置文件:
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:aop="http://www.springframework.org/schema/aop"
xmlns:tx="http://www.springframework.org/schema/tx"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context.xsd
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop.xsd
http://www.springframework.org/schema/tx
http://www.springframework.org/schema/tx/spring-tx.xsd">
上面是大家比较熟悉的Beans配置,其中xmlns为http://www.springframework.org/schema/beans的就是默认的命名空间,其它的属于自定义命名空间.
默认命名空间中定义了 import、alias、bean、beans这几个元素,解析默认的元素就是这几个.
而其它的命名空间中定义的元素,如:mvc、task、context、aop等属于自定义的元素。
我们先看解析默认元素:
private void parseDefaultElement(Element ele, BeanDefinitionParserDelegate delegate) {
if (delegate.nodeNameEquals(ele, "import")) {
//处理import标签,导入资源
this.importBeanDefinitionResource(ele);
} else if (delegate.nodeNameEquals(ele, "alias")) {
//处理alias别名的注册
this.processAliasRegistration(ele);
} else if (delegate.nodeNameEquals(ele, "bean")) {
//处理bean标签
this.processBeanDefinition(ele, delegate);
} else if (delegate.nodeNameEquals(ele, "beans")) {
//注册bean
this.doRegisterBeanDefinitions(ele);
}
}
我们知道IOC主要通过bean标签配置,那么bean的解析就是我们的重点。
protected void processBeanDefinition(Element ele, BeanDefinitionParserDelegate delegate) {
//解析BeanDefinition出来,并封装到BeanDefinitionHolder中
BeanDefinitionHolder bdHolder = delegate.parseBeanDefinitionElement(ele);
if (bdHolder != null) {
//给BeanDefinitionHolder添加属性
bdHolder = delegate.decorateBeanDefinitionIfRequired(ele, bdHolder);
try {
//注册BeanDefinition
BeanDefinitionReaderUtils.registerBeanDefinition(bdHolder, this.getReaderContext().getRegistry());
} catch (BeanDefinitionStoreException var5) {
this.getReaderContext().error("Failed to register bean definition with name '" + bdHolder.getBeanName() + "'", ele, var5);
}
//发送注册事件
this.getReaderContext().fireComponentRegistered(new BeanComponentDefinition(bdHolder));
}
}
这里我们主要看BeanDefinitionHolder的解析,其它方法先跳过,在看具体解析过程前我们先回顾下bean的定义:
<bean id="id名" name="名称1,名称2..." class="包名+类名" scope="prototype|singleton" lazy-init="是否懒加载(true或false)" init-method="初始化方法" destroy-method="销毁方法">
<contructor-arg type="类型" index="位置" name="名称" value="值" ref="对象名"/>
<property name="属性名" value="值" ref="对象名">
</property>
</bean>
上面是定义一个bean的主要配置,接下来我们看bean的解析过程,这是在BeanDefinitionParserDelegate中完成的,类名的意思是BeanDefinition解析的委托。
public BeanDefinitionHolder parseBeanDefinitionElement(Element ele) {
return this.parseBeanDefinitionElement(ele, (BeanDefinition)null);
}
public BeanDefinitionHolder parseBeanDefinitionElement(Element ele, BeanDefinition containingBean) {
//解析id属性
String id = ele.getAttribute("id");
//解析name属性
String nameAttr = ele.getAttribute("name");
List<String> aliases = new ArrayList();
if (StringUtils.hasLength(nameAttr)) {
//把按逗号、分号、空格分开的多个name,添加到别名集合中
String[] nameArr = StringUtils.tokenizeToStringArray(nameAttr, ",; ");
aliases.addAll(Arrays.asList(nameArr));
}
//将id作为bean的名称
String beanName = id;
if (!StringUtils.hasText(id) && !aliases.isEmpty()) {
//如果不存在id,而name存在,就将别名集合的第一个name作为名称
beanName = (String)aliases.remove(0);
if (this.logger.isDebugEnabled()) {
this.logger.debug("No XML 'id' specified - using '" + beanName + "' as bean name and " + aliases + " as aliases");
}
}
if (containingBean == null) {
this.checkNameUniqueness(beanName, aliases, ele);
}
//根据bean节点的配置,解析出一个基本的BeanDefinition
AbstractBeanDefinition beanDefinition = this.parseBeanDefinitionElement(ele, beanName, containingBean);
//下面这部分主要是如果id和name都没有设置,就用class作为bean的名字
if (beanDefinition != null) {
if (!StringUtils.hasText(beanName)) {
try {
if (containingBean != null) {
beanName = BeanDefinitionReaderUtils.generateBeanName(beanDefinition, this.readerContext.getRegistry(), true);
} else {
beanName = this.readerContext.generateBeanName(beanDefinition);
String beanClassName = beanDefinition.getBeanClassName();
if (beanClassName != null && beanName.startsWith(beanClassName) && beanName.length() > beanClassName.length() && !this.readerContext.getRegistry().isBeanNameInUse(beanClassName)) {
aliases.add(beanClassName);
}
}
if (this.logger.isDebugEnabled()) {
this.logger.debug("Neither XML 'id' nor 'name' specified - using generated bean name [" + beanName + "]");
}
} catch (Exception var9) {
this.error(var9.getMessage(), ele);
return null;
}
}
String[] aliasesArray = StringUtils.toStringArray(aliases);
//将BeanDefinition实例封装到BeanDefinitionHolder中,返回
return new BeanDefinitionHolder(beanDefinition, beanName, aliasesArray);
} else {
return null;
}
}
看看parseBeanDefinitionElement这个方法都做了什么
public AbstractBeanDefinition parseBeanDefinitionElement(Element ele, String beanName, BeanDefinition containingBean) {
//添加一个解析状态,这里不细讲了
this.parseState.push(new BeanEntry(beanName));
String className = null;
//将class先解析出来
if (ele.hasAttribute("class")) {
className = ele.getAttribute("class").trim();
}
try {
String parent = null;
//在解析parent属性
if (ele.hasAttribute("parent")) {
parent = ele.getAttribute("parent");
}
//通过className和parent,先创建一个BeanDefinition
AbstractBeanDefinition bd = this.createBeanDefinition(className, parent);
//解析Bean的各种属性
this.parseBeanDefinitionAttributes(ele, beanName, containingBean, bd);
bd.setDescription(DomUtils.getChildElementValueByTagName(ele, "description"));
//解析meta属性
this.parseMetaElements(ele, bd);
//解析lookup-method属性
this.parseLookupOverrideSubElements(ele, bd.getMethodOverrides());
//解析replace-method属性
this.parseReplacedMethodSubElements(ele, bd.getMethodOverrides());
//解析constructor-arg节点
this.parseConstructorArgElements(ele, bd);
//解析property节点
this.parsePropertyElements(ele, bd);
//解析qualifier节点
this.parseQualifierElements(ele, bd);
bd.setResource(this.readerContext.getResource());
bd.setSource(this.extractSource(ele));
AbstractBeanDefinition var7 = bd;
return var7;
} catch (ClassNotFoundException var13) {
this.error("Bean class [" + className + "] not found", ele, var13);
} catch (NoClassDefFoundError var14) {
this.error("Class that bean class [" + className + "] depends on not found", ele, var14);
} catch (Throwable var15) {
this.error("Unexpected failure during bean definition parsing", ele, var15);
} finally {
this.parseState.pop();
}
return null;
}
这里面最有代表性的是解析bean的属性:
public AbstractBeanDefinition parseBeanDefinitionAttributes(Element ele, String beanName, BeanDefinition containingBean, AbstractBeanDefinition bd) {
//解析scope属性
if (ele.hasAttribute("singleton")) {
this.error("Old 1.x 'singleton' attribute in use - upgrade to 'scope' declaration", ele);
} else if (ele.hasAttribute("scope")) {
bd.setScope(ele.getAttribute("scope"));
} else if (containingBean != null) {
bd.setScope(containingBean.getScope());
}
//解析abstract属性
if (ele.hasAttribute("abstract")) {
bd.setAbstract("true".equals(ele.getAttribute("abstract")));
}
//解析lazy-init属性
String lazyInit = ele.getAttribute("lazy-init");
if ("default".equals(lazyInit)) {
lazyInit = this.defaults.getLazyInit();
}
bd.setLazyInit("true".equals(lazyInit));
//解析autowire属性
String autowire = ele.getAttribute("autowire");
bd.setAutowireMode(this.getAutowireMode(autowire));
String dependencyCheck = ele.getAttribute("dependency-check");
bd.setDependencyCheck(this.getDependencyCheck(dependencyCheck));
String autowireCandidate;
if (ele.hasAttribute("depends-on")) {
autowireCandidate = ele.getAttribute("depends-on");
bd.setDependsOn(StringUtils.tokenizeToStringArray(autowireCandidate, ",; "));
}
autowireCandidate = ele.getAttribute("autowire-candidate");
String destroyMethodName;
if (!"".equals(autowireCandidate) && !"default".equals(autowireCandidate)) {
bd.setAutowireCandidate("true".equals(autowireCandidate));
} else {
destroyMethodName = this.defaults.getAutowireCandidates();
if (destroyMethodName != null) {
String[] patterns = StringUtils.commaDelimitedListToStringArray(destroyMethodName);
bd.setAutowireCandidate(PatternMatchUtils.simpleMatch(patterns, beanName));
}
}
if (ele.hasAttribute("primary")) {
bd.setPrimary("true".equals(ele.getAttribute("primary")));
}
if (ele.hasAttribute("init-method")) {
destroyMethodName = ele.getAttribute("init-method");
if (!"".equals(destroyMethodName)) {
bd.setInitMethodName(destroyMethodName);
}
} else if (this.defaults.getInitMethod() != null) {
bd.setInitMethodName(this.defaults.getInitMethod());
bd.setEnforceInitMethod(false);
}
if (ele.hasAttribute("destroy-method")) {
destroyMethodName = ele.getAttribute("destroy-method");
bd.setDestroyMethodName(destroyMethodName);
} else if (this.defaults.getDestroyMethod() != null) {
bd.setDestroyMethodName(this.defaults.getDestroyMethod());
bd.setEnforceDestroyMethod(false);
}
if (ele.hasAttribute("factory-method")) {
bd.setFactoryMethodName(ele.getAttribute("factory-method"));
}
if (ele.hasAttribute("factory-bean")) {
bd.setFactoryBeanName(ele.getAttribute("factory-bean"));
}
return bd;
}
到这里BeanDefinition的解析就完成了,返回了BeanDefinitionHolder对象, 回到前面的processBeanDefinition方法,接下来最重要的是注册BeanDefinition
protected void processBeanDefinition(Element ele, BeanDefinitionParserDelegate delegate) {
//解析BeanDefinition出来,并封装到BeanDefinitionHolder中
BeanDefinitionHolder bdHolder = delegate.parseBeanDefinitionElement(ele);
if (bdHolder != null) {
//给BeanDefinitionHolder添加属性
bdHolder = delegate.decorateBeanDefinitionIfRequired(ele, bdHolder);
try {
//注册BeanDefinition
BeanDefinitionReaderUtils.registerBeanDefinition(bdHolder, this.getReaderContext().getRegistry());
} catch (BeanDefinitionStoreException var5) {
this.getReaderContext().error("Failed to register bean definition with name '" + bdHolder.getBeanName() + "'", ele, var5);
}
//发送注册事件
this.getReaderContext().fireComponentRegistered(new BeanComponentDefinition(bdHolder));
}
}
BeanDefinitionReaderUtils类的静态方法:
public static void registerBeanDefinition(BeanDefinitionHolder definitionHolder, BeanDefinitionRegistry registry) throws BeanDefinitionStoreException {
String beanName = definitionHolder.getBeanName();
//把bean的名称和BeanDefinition关联起来,这里是一个Map集合
registry.registerBeanDefinition(beanName, definitionHolder.getBeanDefinition());
String[] aliases = definitionHolder.getAliases();
if (aliases != null) {
String[] var4 = aliases;
int var5 = aliases.length;
//再把名称和别名关联起来
for(int var6 = 0; var6 < var5; ++var6) {
String alias = var4[var6];
registry.registerAlias(beanName, alias);
}
}
}
注册BeanDefinition是在DefaultListableBeanFactory这个工厂里面,开头介绍过,这个工厂是功能最强大的工厂,里面有个Map集合用于注册所有的BeanDefinition:
private final Map<String, BeanDefinition> beanDefinitionMap = new ConcurrentHashMap(256);
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 var9) {
throw new BeanDefinitionStoreException(beanDefinition.getResourceDescription(), beanName, "Validation of bean definition failed", var9);
}
}
//通过beanName获得BeanDefinition实例
BeanDefinition oldBeanDefinition = (BeanDefinition)this.beanDefinitionMap.get(beanName);
if (oldBeanDefinition != null) {
//如果实例以及存在,又不允许Bean覆盖,就抛异常
if (!this.isAllowBeanDefinitionOverriding()) {
throw new BeanDefinitionStoreException(beanDefinition.getResourceDescription(), beanName, "Cannot register bean definition [" + beanDefinition + "] for bean '" + beanName + "': There is already [" + oldBeanDefinition + "] bound.");
}
//下面都是日志
if (oldBeanDefinition.getRole() < beanDefinition.getRole()) {
if (this.logger.isWarnEnabled()) {
this.logger.warn("Overriding user-defined bean definition for bean '" + beanName + "' with a framework-generated bean definition: replacing [" + oldBeanDefinition + "] with [" + beanDefinition + "]");
}
} else if (!beanDefinition.equals(oldBeanDefinition)) {
if (this.logger.isInfoEnabled()) {
this.logger.info("Overriding bean definition for bean '" + beanName + "' with a different definition: replacing [" + oldBeanDefinition + "] with [" + beanDefinition + "]");
}
} else if (this.logger.isDebugEnabled()) {
this.logger.debug("Overriding bean definition for bean '" + beanName + "' with an equivalent definition: replacing [" + oldBeanDefinition + "] with [" + beanDefinition + "]");
}
//往集合里覆盖原来的BeanDefinition
this.beanDefinitionMap.put(beanName, beanDefinition);
} else {
//这里判断有无其他Bean的创建过程已经开始
if (this.hasBeanCreationStarted()) {
Map var4 = this.beanDefinitionMap;
synchronized(this.beanDefinitionMap) {
//如果有,就添加BeanDefinition
this.beanDefinitionMap.put(beanName, beanDefinition);
//添加名字到BeanDefinition名字集合中
List<String> updatedDefinitions = new ArrayList(this.beanDefinitionNames.size() + 1);
updatedDefinitions.addAll(this.beanDefinitionNames);
updatedDefinitions.add(beanName);
this.beanDefinitionNames = updatedDefinitions;
//从手动注册的Singleton名字中删除该名字
if (this.manualSingletonNames.contains(beanName)) {
Set<String> updatedSingletons = new LinkedHashSet(this.manualSingletonNames);
updatedSingletons.remove(beanName);
this.manualSingletonNames = updatedSingletons;
}
}
} else {
//如果没有开始,就在集合注册新的BeanDefinition
this.beanDefinitionMap.put(beanName, beanDefinition);
//保存Bean的名字
this.beanDefinitionNames.add(beanName);
//从单例名字中删除该名字
this.manualSingletonNames.remove(beanName);
}
this.frozenBeanDefinitionNames = null;
}
if (oldBeanDefinition != null || this.containsSingleton(beanName)) {
this.resetBeanDefinition(beanName);
}
}
总结下上面的所有代码,Spring把XML配置文件中定义的一个个Bean解析出来,创建了一个个BeanDefinition,然后都注册到BeanFacotry这个IOC容器中了。
这样可以说已经完成了IOC的准备工作,接下来就是IOC容器等待对其内部注册的Bean进行依赖注入,那么什么时候会发生注入呢?
也就是我们熟悉了调用BeanFacotry的getBean方法时。
如下:
ClassPathXmlApplicationContext cxt = new ClassPathXmlApplicationContext("applicationContext.xml");
Driver driver = cxt.getBean("driver", Driver.class);
来看看getBean方法,其具体实现在AbstractBeanFactory中:
public <T> T getBean(String name, Class<T> requiredType) throws BeansException {
return this.doGetBean(name, requiredType, (Object[])null, false);
}
就是这个doGetBean方法:
protected <T> T doGetBean(String name, Class<T> requiredType, final Object[] args, boolean typeCheckOnly) throws BeansException {
//通过名称获得Bean的规范名称,主要是去掉前面的&符号
final String beanName = this.transformedBeanName(name);
//通过名字,从缓存中获得一个单例的Bean实例
Object sharedInstance = this.getSingleton(beanName);
Object bean;
if (sharedInstance != null && args == null) {
if (this.logger.isDebugEnabled()) {
if (this.isSingletonCurrentlyInCreation(beanName)) {
this.logger.debug("Returning eagerly cached instance of singleton bean '" + beanName + "' that is not fully initialized yet - a consequence of a circular reference");
} else {
this.logger.debug("Returning cached instance of singleton bean '" + beanName + "'");
}
}
//args参数为空的情况下,创建Bean的对象
//如果该Bean是FactoryBean,就通过FactoryBean创建Bean实例
//如果该Bean是普通的Bean,就直接返回sharedInstance作为Bean实例
bean = this.getObjectForBeanInstance(sharedInstance, name, beanName, (RootBeanDefinition)null);
} else {
if (this.isPrototypeCurrentlyInCreation(beanName)) {
throw new BeanCurrentlyInCreationException(beanName);
}
//获得父BeanFactory
BeanFactory parentBeanFactory = this.getParentBeanFactory();
//如果存在父BeanFactory,并且当前BeanFactory中不存在此名字的Bean
//就在父BeanFactory中查找Bean
if (parentBeanFactory != null && !this.containsBeanDefinition(beanName)) {
String nameToLookup = this.originalBeanName(name);
//通过args参数来创建Bean
if (args != null) {
return parentBeanFactory.getBean(nameToLookup, args);
}
//不需要args参数,直接通过类型创建Bean
return parentBeanFactory.getBean(nameToLookup, requiredType);
}
if (!typeCheckOnly) {
this.markBeanAsCreated(beanName);
}
try {
//准备创建Bean,先创建一个根BeanDefinition
final RootBeanDefinition mbd = this.getMergedLocalBeanDefinition(beanName);
this.checkMergedBeanDefinition(mbd, beanName, args);
//获得Bean的所有依赖bean
String[] dependsOn = mbd.getDependsOn();
String[] var11;
if (dependsOn != null) {
var11 = dependsOn;
int var12 = dependsOn.length;
for(int var13 = 0; var13 < var12; ++var13) {
String dep = var11[var13];
//检查是否存在循环依赖
if (this.isDependent(beanName, dep)) {
throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Circular depends-on relationship between '" + beanName + "' and '" + dep + "'");
}
//注册所有依赖的bean
this.registerDependentBean(dep, beanName);
//把依赖的bean进行初始化
this.getBean(dep);
}
}
//如果是单例,就创建单例的bean
if (mbd.isSingleton()) {
//这里的匿名内部类是通过工厂模式,创建单例Bean
sharedInstance = this.getSingleton(beanName, new ObjectFactory<Object>() {
public Object getObject() throws BeansException {
try {
return AbstractBeanFactory.this.createBean(beanName, mbd, args);
} catch (BeansException var2) {
AbstractBeanFactory.this.destroySingleton(beanName);
throw var2;
}
}
});
bean = this.getObjectForBeanInstance(sharedInstance, name, beanName, mbd);
} else if (mbd.isPrototype()) {
var11 = null;
//如果是多例就直接创建对象
Object prototypeInstance;
try {
this.beforePrototypeCreation(beanName);
prototypeInstance = this.createBean(beanName, mbd, args);
} finally {
this.afterPrototypeCreation(beanName);
}
bean = this.getObjectForBeanInstance(prototypeInstance, name, beanName, mbd);
} else {
//如果scope属性没有配置,就通过Scope类获得Bean实例
String scopeName = mbd.getScope();
Scope scope = (Scope)this.scopes.get(scopeName);
if (scope == null) {
throw new IllegalStateException("No Scope registered for scope name '" + scopeName + "'");
}
try {
Object scopedInstance = scope.get(beanName, new ObjectFactory<Object>() {
public Object getObject() throws BeansException {
AbstractBeanFactory.this.beforePrototypeCreation(beanName);
Object var1;
try {
var1 = AbstractBeanFactory.this.createBean(beanName, mbd, args);
} finally {
AbstractBeanFactory.this.afterPrototypeCreation(beanName);
}
return var1;
}
});
bean = this.getObjectForBeanInstance(scopedInstance, name, beanName, mbd);
} catch (IllegalStateException var21) {
throw new BeanCreationException(beanName, "Scope '" + scopeName + "' 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;
}
}
//将Bean转换为需要的类型
if (requiredType != null && bean != null && !requiredType.isInstance(bean)) {
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;
}
}
下面就重点分析这个createBean了,方法在AbstractAutowireCapableBeanFactory 类中,此类的名字意思大概是抽象的可以自动装配的Bean工厂,也就是说这个类和Spring的自动装配特性相关。
protected Object createBean(String beanName, RootBeanDefinition mbd, Object[] args) throws BeanCreationException {
if (this.logger.isDebugEnabled()) {
this.logger.debug("Creating instance of bean '" + beanName + "'");
}
RootBeanDefinition mbdToUse = mbd;
//获得Bean的Class类型,可见下面就需要用到反射了
Class<?> resolvedClass = this.resolveBeanClass(mbd, beanName, new Class[0]);
if (resolvedClass != null && !mbd.hasBeanClass() && mbd.getBeanClassName() != null) {
//设置Bean的Class
mbdToUse = new RootBeanDefinition(mbd);
mbdToUse.setBeanClass(resolvedClass);
}
try {
//准备Bean的方法重写,如lookup-method、replace-method这些
mbdToUse.prepareMethodOverrides();
} catch (BeanDefinitionValidationException var7) {
throw new BeanDefinitionStoreException(mbdToUse.getResourceDescription(), beanName, "Validation of method overrides failed", var7);
}
Object beanInstance;
try {
//返回Bean或Bean的代理实例
beanInstance = this.resolveBeforeInstantiation(beanName, mbdToUse);
if (beanInstance != null) {
return beanInstance;
}
} catch (Throwable var8) {
throw new BeanCreationException(mbdToUse.getResourceDescription(), beanName, "BeanPostProcessor before instantiation of bean failed", var8);
}
//创建Bean的具体实现
beanInstance = this.doCreateBean(beanName, mbdToUse, args);
if (this.logger.isDebugEnabled()) {
this.logger.debug("Finished creating instance of bean '" + beanName + "'");
}
return beanInstance;
}
protected Object doCreateBean(final String beanName, final RootBeanDefinition mbd, Object[] args) throws BeanCreationException {
BeanWrapper instanceWrapper = null;
//如果是单例,就从缓存中取得单例的Bean
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;
mbd.resolvedTargetType = beanType;
Object var7 = mbd.postProcessingLock;
//调用后置处理器
synchronized(mbd.postProcessingLock) {
if (!mbd.postProcessed) {
try {
this.applyMergedBeanDefinitionPostProcessors(mbd, beanType, beanName);
} catch (Throwable var17) {
throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Post-processing of merged bean definition failed", var17);
}
mbd.postProcessed = true;
}
}
//在容器中缓存单例的实例,防止循环引用
boolean earlySingletonExposure = mbd.isSingleton() && this.allowCircularReferences && this.isSingletonCurrentlyInCreation(beanName);
if (earlySingletonExposure) {
if (this.logger.isDebugEnabled()) {
this.logger.debug("Eagerly caching bean '" + beanName + "' to allow for resolving potential circular references");
}
this.addSingletonFactory(beanName, new ObjectFactory<Object>() {
public Object getObject() throws BeansException {
return AbstractAutowireCapableBeanFactory.this.getEarlyBeanReference(beanName, mbd, bean);
}
});
}
Object exposedObject = bean;
try {
//给Bean的属性初始化
this.populateBean(beanName, mbd, instanceWrapper);
if (exposedObject != null) {
//初始化Bean
exposedObject = this.initializeBean(beanName, exposedObject, mbd);
}
} catch (Throwable var18) {
if (var18 instanceof BeanCreationException && beanName.equals(((BeanCreationException)var18).getBeanName())) {
throw (BeanCreationException)var18;
}
throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Initialization of bean failed", var18);
}
if (earlySingletonExposure) {
Object earlySingletonReference = this.getSingleton(beanName, false);
if (earlySingletonReference != null) {
//当前获得的对象和正在创建的对象如果是同一个对象,就赋值完毕
if (exposedObject == bean) {
exposedObject = earlySingletonReference;
}else if (!this.allowRawInjectionDespiteWrapping && this.hasDependentBean(beanName)) {
String[] dependentBeans = this.getDependentBeans(beanName);
Set<String> actualDependentBeans = new LinkedHashSet(dependentBeans.length);
String[] var12 = dependentBeans;
int var13 = dependentBeans.length;
for(int var14 = 0; var14 < var13; ++var14) {
String dependentBean = var12[var14];
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);
}}
该方法的内容比较多,这里就不对所有细节进行分析了,主要看两个部分:
1、创建Bean的createBeanInstance
2、初始化属性的populateBean
protected BeanWrapper createBeanInstance(String beanName, RootBeanDefinition mbd, Object[] args) {
//获得类型
Class<?> beanClass = this.resolveBeanClass(mbd, beanName, new Class[0]);
//如果类不能访问,抛异常
if (beanClass != null && !Modifier.isPublic(beanClass.getModifiers()) && !mbd.isNonPublicAccessAllowed()) {
throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Bean class isn't public, and non-public access not allowed: " + beanClass.getName());
} else if (mbd.getFactoryMethodName() != null) {
//如果存在工厂方法,就调用工厂方法创建对象
return this.instantiateUsingFactoryMethod(beanName, mbd, args);
} else {
boolean resolved = false;
boolean autowireNecessary = false;
if (args == null) {
Object var7 = mbd.constructorArgumentLock;
synchronized(mbd.constructorArgumentLock) {
if (mbd.resolvedConstructorOrFactoryMethod != null) {
resolved = true;
autowireNecessary = mbd.constructorArgumentsResolved;
}
}
}
if (resolved) {
//如果自动装配必要,就调用自动装配的构造方法创建对象
//否则使用无参构造方法创建对象
return autowireNecessary ? this.autowireConstructor(beanName, mbd, (Constructor[])null, (Object[])null) : this.instantiateBean(beanName, mbd);
} else {
Constructor<?>[] ctors = this.determineConstructorsFromBeanPostProcessors(beanClass, beanName);
//如果没有无参的构造方法,就用无参的构造方法,有就调用有参的构造方法
return ctors == null && mbd.getResolvedAutowireMode() != 3 && !mbd.hasConstructorArgumentValues() && ObjectUtils.isEmpty(args) ? this.instantiateBean(beanName, mbd) : this.autowireConstructor(beanName, mbd, ctors, args);
}
}
}
先看看无参的构造方法是怎么调用的
protected BeanWrapper instantiateBean(final String beanName, final RootBeanDefinition mbd) {
try {
Object beanInstance;
if (System.getSecurityManager() != null) {
beanInstance = AccessController.doPrivileged(new PrivilegedAction<Object>() {
public Object run() {
return AbstractAutowireCapableBeanFactory.this.getInstantiationStrategy().instantiate(mbd, beanName, AbstractAutowireCapableBeanFactory.this);
}
}, this.getAccessControlContext());
} else {
beanInstance = this.getInstantiationStrategy().instantiate(mbd, beanName, this);
}
BeanWrapper bw = new BeanWrapperImpl(beanInstance);
this.initBeanWrapper(bw);
return bw;
} catch (Throwable var6) {
throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Instantiation of bean failed", var6);
}
}
这里的关键在于getInstantiationStrategy().instantiate这里,getInstantiationStrategy()这个方法返回的对象是CglibSubclassingInstantiationStrategy类,通过名字我们可以大概了解这个类是使用Cglib进行对象实例化的策略,继承于SimpleInstantiationStrategy类,再看instantiate方法:
public Object instantiate(RootBeanDefinition bd, String beanName, BeanFactory owner) {
//判断有无方法覆盖
if (bd.getMethodOverrides().isEmpty()) {
Object var5 = bd.constructorArgumentLock;
Constructor constructorToUse;
synchronized(bd.constructorArgumentLock) {
constructorToUse = (Constructor)bd.resolvedConstructorOrFactoryMethod;
if (constructorToUse == null) {
//获得bean的类型
final Class<?> clazz = bd.getBeanClass();
//如果是接口不能实例化,则抛异常
if (clazz.isInterface()) {
throw new BeanInstantiationException(clazz, "Specified class is an interface");
}
//这里是获得构造方法
try {
if (System.getSecurityManager() != null) {
constructorToUse = (Constructor)AccessController.doPrivileged(new PrivilegedExceptionAction<Constructor<?>>() {
public Constructor<?> run() throws Exception {
return clazz.getDeclaredConstructor((Class[])null);
}
});
} else {
constructorToUse = clazz.getDeclaredConstructor((Class[])null);
}
bd.resolvedConstructorOrFactoryMethod = constructorToUse;
} catch (Throwable var9) {
throw new BeanInstantiationException(clazz, "No default constructor found", var9);
}
}
}
//通过构造方法进行实例化
return BeanUtils.instantiateClass(constructorToUse, new Object[0]);
} else {
//这里通过CGLIB完成实例化
return this.instantiateWithMethodInjection(bd, beanName, owner);
}
}
这里通过反射或CGLIB完成了对象的实例化,但对象的属性还没有初始化,再看属性的初始化:
protected void populateBean(String beanName, RootBeanDefinition mbd, BeanWrapper bw) {
//获得所有属性的值
PropertyValues pvs = mbd.getPropertyValues();
//如果对象为null,则抛出异常
if (bw == null) {
if (!((PropertyValues)pvs).isEmpty()) {
throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Cannot apply property values to null instance");
}
} else {
boolean continueWithPropertyPopulation = true;
if (!mbd.isSynthetic() && this.hasInstantiationAwareBeanPostProcessors()) {
Iterator var6 = this.getBeanPostProcessors().iterator();
//初始化属性前,调用bean的PostProcessor后置处理器
while(var6.hasNext()) {
BeanPostProcessor bp = (BeanPostProcessor)var6.next();
if (bp instanceof InstantiationAwareBeanPostProcessor) {
InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor)bp;
if (!ibp.postProcessAfterInstantiation(bw.getWrappedInstance(), beanName)) {
continueWithPropertyPopulation = false;
break;
}
}
}
}
if (continueWithPropertyPopulation) {
if (mbd.getResolvedAutowireMode() == 1 || mbd.getResolvedAutowireMode() == 2) {
MutablePropertyValues newPvs = new MutablePropertyValues((PropertyValues)pvs);
//按名字对属性进行自动装配
if (mbd.getResolvedAutowireMode() == 1) {
this.autowireByName(beanName, mbd, bw, newPvs);
}
//按类型对属性进行自动装配
if (mbd.getResolvedAutowireMode() == 2) {
this.autowireByType(beanName, mbd, bw, newPvs);
}
pvs = newPvs;
}
//存在属性初始化的后置处理器
boolean hasInstAwareBpps = this.hasInstantiationAwareBeanPostProcessors();
//需要进行依赖检查
boolean needsDepCheck = mbd.getDependencyCheck() != 0;
if (hasInstAwareBpps || needsDepCheck) {
//获得属性的描述符
PropertyDescriptor[] filteredPds = this.filterPropertyDescriptorsForDependencyCheck(bw, mbd.allowCaching);
if (hasInstAwareBpps) {
Iterator var9 = this.getBeanPostProcessors().iterator();
while(var9.hasNext()) {
BeanPostProcessor bp = (BeanPostProcessor)var9.next();
if (bp instanceof InstantiationAwareBeanPostProcessor) {
InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor)bp;
//调用初始化属性的后置处理器处理属性值
pvs = ibp.postProcessPropertyValues((PropertyValues)pvs, filteredPds, bw.getWrappedInstance(), beanName);
if (pvs == null) {
return;
}
}
}
}
//检查依赖
if (needsDepCheck) {
this.checkDependencies(beanName, mbd, filteredPds, (PropertyValues)pvs);
}
}
//把属性注入到Bean中
this.applyPropertyValues(beanName, mbd, bw, (PropertyValues)pvs);
}
}
}
最后我们看看属性怎么注入进去的,applyPropertyValues方法主要实现的是属性值的类型转换和赋值。
protected void applyPropertyValues(String beanName, BeanDefinition mbd, BeanWrapper bw, PropertyValues pvs) {
if (pvs != null && !pvs.isEmpty()) {
MutablePropertyValues mpvs = null;
//设置了安全上下文
if (System.getSecurityManager() != null && bw instanceof BeanWrapperImpl) {
((BeanWrapperImpl)bw).setSecurityContext(this.getAccessControlContext());
}
List original;
if (pvs instanceof MutablePropertyValues) {
//转换为可变属性值
mpvs = (MutablePropertyValues)pvs;
//如果已经转换过
if (mpvs.isConverted()) {
try {
//直接赋值,结束注入
bw.setPropertyValues(mpvs);
return;
} catch (BeansException var18) {
throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Error setting property values", var18);
}
}
//获得原始的值
original = mpvs.getPropertyValueList();
} else {
//获得原始值
original = Arrays.asList(pvs.getPropertyValues());
}
//获得类型转换器
TypeConverter converter = this.getCustomTypeConverter();
if (converter == null) {
converter = bw;
}
//属性值的处理器
BeanDefinitionValueResolver valueResolver = new BeanDefinitionValueResolver(this, beanName, mbd, (TypeConverter)converter);
//属性值的深复制副本
List<PropertyValue> deepCopy = new ArrayList(original.size());
boolean resolveNecessary = false;
Iterator var11 = original.iterator();
while(true) {
while(var11.hasNext()) {
PropertyValue pv = (PropertyValue)var11.next();
//如果值已经转换,就直接添加到副本中
if (pv.isConverted()) {
deepCopy.add(pv);
} else {
//获得属性名
String propertyName = pv.getName();
//获得属性原始值
Object originalValue = pv.getValue();
//获得处理后的属性值
Object resolvedValue = valueResolver.resolveValueIfNecessary(pv, originalValue);
Object convertedValue = resolvedValue;
boolean convertible = bw.isWritableProperty(propertyName) && !PropertyAccessorUtils.isNestedOrIndexedProperty(propertyName);
//如果可以转换,就用自定义的转换器转换
if (convertible) {
convertedValue = this.convertForProperty(resolvedValue, propertyName, bw, (TypeConverter)converter);
}
if (resolvedValue == originalValue) {
//如果处理后的值和原始值相同,可以转换,就保存转换后的值
if (convertible) {
pv.setConvertedValue(convertedValue);
}
//添加到副本中
deepCopy.add(pv);
} else if (convertible && originalValue instanceof TypedStringValue && !((TypedStringValue)originalValue).isDynamic() && !(convertedValue instanceof Collection) && !ObjectUtils.isArray(convertedValue)) {
//如果可以转换并且是字符串类型不是动态字符串和集合以及数组
//就保存转换的值,添加到副本
pv.setConvertedValue(convertedValue);
deepCopy.add(pv);
} else {
resolveNecessary = true;
//重写封装了属性值
deepCopy.add(new PropertyValue(pv, convertedValue));
}
}
}
//设置为已经转换过
if (mpvs != null && !resolveNecessary) {
mpvs.setConverted();
}
//把深拷贝的属性值注入到bean中
try {
bw.setPropertyValues(new MutablePropertyValues(deepCopy));
return;
} catch (BeansException var19) {
throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Error setting property values", var19);
}
}
}
}
总结
到这里Spring的IOC流程基本完成了,当然还有很多细节我们没有深入进去,因为Spring的代码实在是太浩瀚了,完全把每个细节分析透彻需要太多的篇幅,我们先把IOC的主干弄清楚,IOC的主要过程是:
- 解析XML配置文件或注解(解析注解部分大家可以自己学习)
- 将配置文件中的节点,解析成一个个的BeanDefinition实例
- 将BeanDefinition实例注册到BeanFactory中
- 通过getBean获得BeanFactory中的Bean
- 通过反射或CGLIB实例化Bean,并完成属性的注入
通过学习Spring的源码,我们可以学习到很多好的编程思想和设计模式,用在自己的开发实践中。
这么长的文章都能看完的同学,给自己点个赞:)
大家如果需要学习其他Java知识点,戳这里 超详细的Java知识点汇总