写点什么

Spring 源码解析(一)IOC,终于找到一个看得懂的 JVM 内存模型了

用户头像
极客good
关注
发布于: 刚刚

}


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.setFactoryBeanNa


【一线大厂Java面试题解析+核心总结学习笔记+最新架构讲解视频+实战项目源码讲义】
浏览器打开:qq.cn.hn/FTf 免费领取
复制代码


me(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;

用户头像

极客good

关注

还未添加个人签名 2021.03.18 加入

还未添加个人简介

评论

发布
暂无评论
Spring源码解析(一)IOC,终于找到一个看得懂的JVM内存模型了