Spring容器系列-bean的生命周期
bean 的生命周期从调用 beanFactory 的 getBean 开始,到这个 bean 被销毁,可以总结为以下七个阶段:
1. 处理名称,检查缓存
2. 处理父子容器
3. 处理 dependsOn
4. 选择 scope 策略
5. 创建 bean
6. 类型转换处理
7. 销毁 bean
下面我们看AbstractBeanFactory#doGetBean方法来依次讲解:
1 protected <T> T doGetBean(String name, @Nullable Class<T> requiredType, @Nullable Object[] args, boolean typeCheckOnly) throws BeansException { 2 //1.处理bean名称解析 3 String beanName = this.transformedBeanName(name); 4 //检查是否存在缓存中,一级二级三级 5 Object sharedInstance = this.getSingleton(beanName); 6 Object beanInstance; 7 //从单例缓存中判断是否存在这个示例,可能来源于Spring启动的时候,也有可能来源于Spring 启动时初始化了非懒加载的对象 8 if (sharedInstance != null && args == null) { 9 if (this.logger.isTraceEnabled()) { 10 if (this.isSingletonCurrentlyInCreation(beanName)) { 11 this.logger.trace("Returning eagerly cached instance of singleton bean '" + beanName + "' that is not fully initialized yet - a consequence of a circular reference"); 12 } else { 13 this.logger.trace("Returning cached instance of singleton bean '" + beanName + "'"); 14 } 15 } 16 //如果单例工厂存在这个bean,则通过调用getObject方法获取bean实例 17 beanInstance = this.getObjectForBeanInstance(sharedInstance, name, beanName, (RootBeanDefinition)null); 18 } else { 19 //如果当前线程存在这个实例,则抛出异常 20 if (this.isPrototypeCurrentlyInCreation(beanName)) { 21 throw new BeanCurrentlyInCreationException(beanName); 22 } 23 //2.获取当前bean工厂的父工厂,然后获取bean,此处是递归查找 24 BeanFactory parentBeanFactory = this.getParentBeanFactory(); 25 if (parentBeanFactory != null && !this.containsBeanDefinition(beanName)) { 26 String nameToLookup = this.originalBeanName(name); 27 if (parentBeanFactory instanceof AbstractBeanFactory) { 28 29 return ((AbstractBeanFactory)parentBeanFactory).doGetBean(nameToLookup, requiredType, args, typeCheckOnly); 30 } 31 32 if (args != null) { 33 //调用父工厂的getBean方法 34 return parentBeanFactory.getBean(nameToLookup, args); 35 } 36 37 if (requiredType != null) { 38 //根据类型获取bean 39 return parentBeanFactory.getBean(nameToLookup, requiredType); 40 } 41 42 return parentBeanFactory.getBean(nameToLookup); 43 } 44 //如果参数为检查类型,则设置名称为beanName的bean实例已经创建的标识 45 if (!typeCheckOnly) { 46 this.markBeanAsCreated(beanName); 47 } 48 49 StartupStep beanCreation = this.applicationStartup.start("spring.beans.instantiate").tag("beanName", name); 50 51 try { 52 if (requiredType != null) { 53 beanCreation.tag("beanType", requiredType::toString); 54 } 55 56 RootBeanDefinition mbd = this.getMergedLocalBeanDefinition(beanName); 57 this.checkMergedBeanDefinition(mbd, beanName, args); 58 //3.获取bean的依赖属性 59 String[] dependsOn = mbd.getDependsOn(); 60 String[] var12; 61 if (dependsOn != null) { 62 var12 = dependsOn; 63 int var13 = dependsOn.length; 64 65 for(int var14 = 0; var14 < var13; ++var14) { 66 String dep = var12[var14]; 67 //检查是否存在循环依赖 68 if (this.isDependent(beanName, dep)) { 69 throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Circular depends-on relationship between '" + beanName + "' and '" + dep + "'"); 70 } 71 //向注册器中注册这个依赖的bean 72 this.registerDependentBean(dep, beanName); 73 74 try { 75 //获取并解决当前bean 76 this.getBean(dep); 77 } catch (NoSuchBeanDefinitionException var31) { 78 throw new BeanCreationException(mbd.getResourceDescription(), beanName, "'" + beanName + "' depends on missing bean '" + dep + "'", var31); 79 } 80 } 81 } 82 //根据 scope 处理当前bean 83 if (mbd.isSingleton()) { 84 sharedInstance = this.getSingleton(beanName, () -> { 85 try { 86 return this.createBean(beanName, mbd, args); 87 } catch (BeansException var5) { 88 this.destroySingleton(beanName); 89 throw var5; 90 } 91 }); 92 beanInstance = this.getObjectForBeanInstance(sharedInstance, name, beanName, mbd); 93 } else if (mbd.isPrototype()) { 94 var12 = null; 95 96 Object prototypeInstance; 97 try { 98 this.beforePrototypeCreation(beanName); 99 prototypeInstance = this.createBean(beanName, mbd, args); 100 } finally { 101 this.afterPrototypeCreation(beanName); 102 } 103 104 beanInstance = this.getObjectForBeanInstance(prototypeInstance, name, beanName, mbd); 105 } else { 106 String scopeName = mbd.getScope(); 107 if (!StringUtils.hasLength(scopeName)) { 108 throw new IllegalStateException("No scope name defined for bean '" + beanName + "'"); 109 } 110 //5.类型转换 111 Scope scope = (Scope)this.scopes.get(scopeName); 112 if (scope == null) { 113 throw new IllegalStateException("No Scope registered for scope name '" + scopeName + "'"); 114 } 115 116 try { 117 Object scopedInstance = scope.get(beanName, () -> { 118 this.beforePrototypeCreation(beanName); 119 120 Object var4; 121 try { 122 var4 = this.createBean(beanName, mbd, args); 123 } finally { 124 this.afterPrototypeCreation(beanName); 125 } 126 127 return var4; 128 }); 129 beanInstance = this.getObjectForBeanInstance(scopedInstance, name, beanName, mbd); 130 } catch (IllegalStateException var30) { 131 throw new ScopeNotActiveException(beanName, scopeName, var30); 132 } 133 } 134 } catch (BeansException var32) { 135 beanCreation.tag("exception", var32.getClass().toString()); 136 beanCreation.tag("message", String.valueOf(var32.getMessage())); 137 //清除创建bean 138 this.cleanupAfterBeanCreationFailure(beanName); 139 throw var32; 140 } finally { 141 beanCreation.end(); 142 } 143 } 144 145 return this.adaptBeanInstance(name, beanInstance, requiredType); 146 }
DefaultSingletonBeanRegistry#getSingleton方法:
通过调用getSingleton方法,这里针对单例对象会检查一级、二级、三级缓存
1 //singletonObjects 一级缓存,存放单例成品对象 2 private final Map<String, Object> singletonObjects = new ConcurrentHashMap(256); 3 //singletonFactories 三级缓存,存放单例工厂对象 4 private final Map<String, ObjectFactory<?>> singletonFactories = new HashMap(16); 5 //earlySingletonObjects 二级缓存,存放单例工厂的产品对象 6 private final Map<String, Object> earlySingletonObjects = new ConcurrentHashMap(16); 7 @Nullable 8 protected Object getSingleton(String beanName, boolean allowEarlyReference) { 9 Object singletonObject = this.singletonObjects.get(beanName); 10 if (singletonObject == null && this.isSingletonCurrentlyInCreation(beanName)) { 11 singletonObject = this.earlySingletonObjects.get(beanName); 12 if (singletonObject == null && allowEarlyReference) { 13 synchronized(this.singletonObjects) { 14 singletonObject = this.singletonObjects.get(beanName); 15 if (singletonObject == null) { 16 singletonObject = this.earlySingletonObjects.get(beanName); 17 if (singletonObject == null) { 18 ObjectFactory<?> singletonFactory = (ObjectFactory)this.singletonFactories.get(beanName); 19 if (singletonFactory != null) { 20 singletonObject = singletonFactory.getObject(); 21 this.earlySingletonObjects.put(beanName, singletonObject); 22 this.singletonFactories.remove(beanName); 23 } 24 } 25 } 26 } 27 } 28 } 29 return singletonObject; 30 }
2. 处理父子容器
1)如果当前容器根据名字找不到这个 bean,此时若父容器存在,则执行父容器的 getBean 流程
2)父子容器的 bean 名称可以重复
3. 处理 dependsOn
1)如果当前 bean 有通过 dependsOn 指定了非显式依赖的 bean,这一步会提前创建这些 dependsOn 的 bean
2)所谓非显式依赖,就是指两个 bean 之间不存在直接依赖关系,但需要控制它们的创建先后顺序
4. 选择 scope 策略
1 if (mbd.isSingleton()) { 2 //如果是单例类型的bean,通过调用createBean方法尽心创建, 3 sharedInstance = this.getSingleton(beanName, () -> { 4 try { 5 return this.createBean(beanName, mbd, args); 6 } catch (BeansException var5) { 7 //如果创建bean发生异常,则由于当前bean可能被添加在单例池中,调用销毁方法销毁当前bean 8 this.destroySingleton(beanName); 9 throw var5; 10 } 11 }); 12 beanInstance = this.getObjectForBeanInstance(sharedInstance, name, beanName, mbd); 13 } else if (mbd.isPrototype()) { 14 var12 = null; 15 //如果当前bean是多例的,则实时创建 16 Object prototypeInstance; 17 try { 18 //在threadlocal中设置这个bean的标志位,防止同一个线程重复创建bean造成资源浪费 19 this.beforePrototypeCreation(beanName); 20 //创建bean实例 21 prototypeInstance = this.createBean(beanName, mbd, args); 22 } finally { 23 //清除threadlocal标志位 24 this.afterPrototypeCreation(beanName); 25 } 26 27 beanInstance = this.getObjectForBeanInstance(prototypeInstance, name, beanName, mbd); 28 } else { 29 //处理bean的作用范围为 request、session的bean 30 String scopeName = mbd.getScope(); 31 if (!StringUtils.hasLength(scopeName)) { 32 throw new IllegalStateException("No scope name defined for bean '" + beanName + "'"); 33 } 34 35 Scope scope = (Scope)this.scopes.get(scopeName); 36 if (scope == null) { 37 throw new IllegalStateException("No Scope registered for scope name '" + scopeName + "'"); 38 } 39 40 try { 41 Object scopedInstance = scope.get(beanName, () -> { 42 this.beforePrototypeCreation(beanName); 43 44 Object var4; 45 try { 46 var4 = this.createBean(beanName, mbd, args); 47 } finally { 48 this.afterPrototypeCreation(beanName); 49 } 50 51 return var4; 52 }); 53 beanInstance = this.getObjectForBeanInstance(scopedInstance, name, beanName, mbd); 54 } catch (IllegalStateException var30) { 55 throw new ScopeNotActiveException(beanName, scopeName, var30); 56 } 57 }
标签:生命周期,name,mbd,Spring,beanName,bean,scope,null From: https://www.cnblogs.com/hld123/p/18253244