Spring源码系列一:Ioc 设计理念
1.怎么理解Ioc?
IoC(Inversion of Control) 也称为依赖注入(dependency injection, DI)。它是一个对象定义依赖关系的过程,也就是说,对象只通过构造函数参数、工厂方法的参数或对象实例构造或从工厂方法返回后在对象实例上设置的属性来定义它们所使用的其他对象。然后容器在创建bean时注入这些依赖项。
这个过程基本上是bean的逆过程,因此称为控制反转(IoC)。
所以Ioc可以理解为,Ioc是一种设计思想,而实现这种设计思想的方法叫做DI
2.Ioc的执行过程
-
装配bean的方式:xml @compomentScan +@compoment @bean @import @importResource @conditional
-
通过BeanDefinitionReader解析成spring能控制的最小单元bean->BeanDefinition 所有bean的共性:beanClass=xxx.class abstract=false lazyInit=false scope=singleton autowireMode=0 (0-> no 1->byType 2->byName 3->Constructor)
ScannedGenericBeanDefinition: @CompomentScan + @Compoment AnnotatedGenericBeanDefinition: @Import注解
ConfigurationClassBeanDefinition: @bean -
BeanDefinitionRegistry(Spring中最重要的实现类,DefaultListableBeanFactory 即是beanFactory,也是一个注册器,registerBeanDefinition(beanName,beanDefinition)) bean注册器把上述装配的xxx.class都注册到beanDefinitionMap(CurrentHashMap)缓存
-
容器启动时加载 !bd.isAbstract() && bd.isSingleton() && !bd.isLazyInit() 所有非懒加载的,非抽象的,单例的bean;
-
首先1.doGetBean(name, null, null, false) -> Object sharedInstance = getSingleton(beanName) -> Object singletonObject = this.singletonObjects.get(beanName)
先判断单例对象池中是否存在?
存在直接返回bean-> bean = getObjectForBeanInstance(sharedInstance, name, beanName, null);
是否是factoryBean类型?
if (!(beanInstance instanceof FactoryBean) || BeanFactoryUtils.isFactoryDereference(name)) {
return beanInstance;
}
getObjectFromFactoryBean(factory, beanName, !synthetic) -
创建bean
单例对象池中不存在,此时判断Bean的类型:单例,原型?
原型:直接 createBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args)
单例:再一次从单例对象池中获取,如果没有调用singletonFactory.getObject()去创建bean
doCreateBean(beanName, mbdToUse, args)->
BeanWrapper beanWrapper =createBeanInstance(beanName, mbd, args) ->
addSingletonFactory(beanName, getEarlyBeanReference(beanName, mbd, bean))->
populateBean(beanName, mbd, instanceWrapper)->
initializeBean(beanName, exposedObject, mbd)->
addSingleton(beanName, singletonObject) -
DefaultListableBeanFactory 实现了BeanDefinitionRegistry ,ConfigurableListableBeanFactory
所以就会同时拥有注册bean的功能,和获取所有bean的功能