Spring源码学习-1.IOC-DefaultListableBeanFactory

来源:互联网 发布:windows to go怎么用 编辑:程序博客网 时间:2024/05/06 11:25

1,spring简介

                       |   spring事务    spring应用
                       |
                       |   
spring AOP  |    spring JDBC/ORM SpringMVC Spring远程支持
                       |
                       |    SpringIOC模块(BeanFactory 应用上下文 各种支持实现)

2,Spring Frameword 核心简介:IOC容器实现(依赖反转原理)

1.注入方式:接口注入,setter注入,构造器注入

2.各个组件功能介绍

BeanFactory:IoC容器功能规范

BeanDefinition:管理各种对象与他们之间的依赖关系,提供了相应的beanClass、scope、lazyInit属性

3.SpringIoc设计结构

1.BeanFactory <- HierarchicalBeanFactory <-ConfigurableBeanFactory

HierarchicalBeanFactory:继承 BeanFactory ,增加getParentBeanFactory()方法,让Beanfactory具备双亲IOC功能
ConfigurableBeanFactory:Bean后置管理器
2. WebApplicationContext(+ThemeSource) or ConfigurableApplicationContext
<--ApplicationContext(+HierarchicalBeanFactory)(+MessageSource, ApplicationEventPublisher, ResourcePatternResolver)
<--ListableBeanFactory<-BeanFactory
ListableBeanFactory:细化接口功能,如定义getBeanDefinitionNames()功能

通过继承下面三个接口,添加了高级容器的特性支持
MessageSource:这些信息源的扩展功能使得支持国际化
ApplicationEventPublisher:支持应用事件,在上下文中引入事件机制
ResourcePatternResolver:访问资源

3.对于1中的设计路线,主要实现方法是DefaultListableBeanFactory

4.BeanFactory 编程实现

<pre name="code" class="java">public class Demo1 {/** *  */@Testpublic void helloWorld(){/* * XMLBeanFactory继承的类 * public class DefaultListableBeanFactory extends AbstractAutowireCapableBeanFactory   implements ConfigurableListableBeanFactory, BeanDefinitionRegistry, Serializable */DefaultListableBeanFactory beanFactory = new DefaultListableBeanFactory();RootBeanDefinition siglentonBeanDefinition = new RootBeanDefinition(Model.class);RootBeanDefinition prototypeBeanDefinition = new RootBeanDefinition(Model.class);//调用构造器设置属性值ConstructorArgumentValues a = new ConstructorArgumentValues();a.addIndexedArgumentValue(0, "siglentonBeanId");a.addIndexedArgumentValue(1, "siglentonBeanName");siglentonBeanDefinition.setConstructorArgumentValues(a);//setXXX()设置属性值MutablePropertyValues propertyValues = new MutablePropertyValues();propertyValues.addPropertyValue(new PropertyValue("id", "prototypeBeanId"));propertyValues.addPropertyValue(new PropertyValue("name", "prototypeBeanName"));prototypeBeanDefinition.setPropertyValues(propertyValues);prototypeBeanDefinition.setScope("prototype");//一个单例Bean 一个原型BeanbeanFactory.registerBeanDefinition("siglentonBean", siglentonBeanDefinition);beanFactory.registerBeanDefinition("prototypeBean", prototypeBeanDefinition);Model out1,out2,out3,out4 = null;if(beanFactory.containsBean("siglentonBean")){System.out.println("siglentonBean isSingleton:"+beanFactory.isSingleton("siglentonBean"));System.out.println("prototypeBean isSingleton:"+beanFactory.isSingleton("prototypeBean"));System.out.println("Test prototype or siglentonBean");out1 = (Model) beanFactory.getBean("siglentonBean");out3 = (Model) beanFactory.getBean("siglentonBean");out2 = (Model) beanFactory.getBean("prototypeBean");out4 = (Model) beanFactory.getBean("prototypeBean");System.out.println(out1.getId()+":::::siglentonBean1:"+out1.toString()+"     "+out3.getId()+":::::siglentonBean2:"+out3.toString());System.out.println(out2.getId()+":::::prototypeBean1:"+out2.toString()+"     "+out4.getId()+":::::prototypeBean2:"+out4.toString());}}}  class Model {private String id;private String name;public String getId() {return id;}public void setId(String id) {this.id = id;}public String getName() {return name;}public void setName(String name) {this.name = name;}public Model(String id, String name) {super();this.id = id;this.name = name;}public Model() {super();}}

运行结果:
siglentonBean isSingleton:true
prototypeBean isSingleton:false
Test prototype or siglentonBean
siglentonBeanId:::::siglentonBean1:Day001Demo.Model@6acd5f8b     siglentonBeanId:::::siglentonBean2:Day001Demo.Model@6acd5f8b
prototypeBeanId:::::prototypeBean1:Day001Demo.Model@513bd574     prototypeBeanId:::::prototypeBean2:Day001Demo.Model@2f3adc56


在DefaultListableBeanFactory 调用父类的构造函数是,其中有两个构造函数有一些意义.//RootBeanDefinition的构造函数,设置了Bean的Class属性
public RootBeanDefinition(Class beanClass) {
super();
setBeanClass(beanClass);
}

继续往下走:AbstractBeanDefinition类的构造函数

</pre><pre name="code" class="java">protected AbstractBeanDefinition() {this(null, null);}/** * Create a new AbstractBeanDefinition with the given * constructor argument values and property values.         *两种方法给Bean设置默认值 */protected AbstractBeanDefinition(ConstructorArgumentValues cargs, MutablePropertyValues pvs) {setConstructorArgumentValues(cargs);setPropertyValues(pvs);}

</pre>接下来调用registerBeanDefinition方法,注册BeanDefinition<p></p><p><span style="background-color:rgb(240,240,240)"></span></p><pre name="code" class="java">public void registerBeanDefinition(String beanName, BeanDefinition beanDefinition)throws BeanDefinitionStoreException {Assert.hasText(beanName, "'beanName' must not be empty");Assert.notNull(beanDefinition, "BeanDefinition must not be null");if (beanDefinition instanceof AbstractBeanDefinition) {try {// 校验beanClass是否存在((AbstractBeanDefinition) beanDefinition).validate();}catch (BeanDefinitionValidationException ex) {throw new BeanDefinitionStoreException(beanDefinition.getResourceDescription(), beanName,"Validation of bean definition failed", ex);}}synchronized (this.beanDefinitionMap) {Object oldBeanDefinition = this.beanDefinitionMap.get(beanName);//如果Map中已经有这个beanName ,并且不允许覆盖原来的beanName的话,抛出异常.如果允许就继续允许,并在日志中留下覆盖的记录if (oldBeanDefinition != null) {if (!this.allowBeanDefinitionOverriding) {throw new BeanDefinitionStoreException(beanDefinition.getResourceDescription(), beanName,"Cannot register bean definition [" + beanDefinition + "] for bean '" + beanName +"': There is already [" + oldBeanDefinition + "] bound.");}else {if (this.logger.isInfoEnabled()) {this.logger.info("Overriding bean definition for bean '" + beanName +"': replacing [" + oldBeanDefinition + "] with [" + beanDefinition + "]");}}}else {this.beanDefinitionNames.add(beanName);this.frozenBeanDefinitionNames = null;}//放入Map中this.beanDefinitionMap.put(beanName, beanDefinition);resetBeanDefinition(beanName);}}
接下来就是关键的方法getBean
这个得到Bean实例的实现代码如下:

protected Object doGetBean(final String name, final Class requiredType, final Object[] args, boolean typeCheckOnly) throws BeansException {//name有可能是alias ,也有能是beanName的名字,让他统一转成BeanNamefinal String beanName = transformedBeanName(name);Object bean = null;// 查看singletonObjects这个Map中是否已经有了这个实例或者半成品实例//private final Map singletonObjects = CollectionFactory.createConcurrentMapIfPossible(16);//这是一个线程安全的MapObject sharedInstance = getSingleton(beanName);if (sharedInstance != null) {if (logger.isDebugEnabled()) {if (isSingletonCurrentlyInCreation(beanName)) {logger.debug("Returning eagerly cached instance of singleton bean '" + beanName +"' that is not fully initialized yet - a consequence of a circular reference");}else {logger.debug("Returning cached instance of singleton bean '" + beanName + "'");}}//创建实例bean = getObjectForBeanInstance(sharedInstance, name, beanName, null);}else {// Fail if we're already creating this bean instance:// We're assumably within a circular reference.if (isPrototypeCurrentlyInCreation(beanName)) {throw new BeanCurrentlyInCreationException(beanName);}// Check if bean definition exists in this factory.BeanFactory parentBeanFactory = getParentBeanFactory();if (parentBeanFactory != null && !containsBeanDefinition(beanName)) {// Not found -> check parent.String nameToLookup = originalBeanName(name);if (args != null) {// 父BeanFactory已经加载的话,直接返回Beanreturn parentBeanFactory.getBean(nameToLookup, args);}else {// No args -> delegate to standard getBean method.return parentBeanFactory.getBean(nameToLookup, requiredType);}}if (!typeCheckOnly) {markBeanAsCreated(beanName);}final RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);checkMergedBeanDefinition(mbd, beanName, args);// Guarantee initialization of beans that the current bean depends on.String[] dependsOn = mbd.getDependsOn();if (dependsOn != null) {for (int i = 0; i < dependsOn.length; i++) {String dependsOnBean = dependsOn[i];getBean(dependsOnBean);registerDependentBean(dependsOnBean, beanName);}}// Create bean instance.if (mbd.isSingleton()) {sharedInstance = getSingleton(beanName, new ObjectFactory() {public Object getObject() throws BeansException {try {return createBean(beanName, mbd, args);}catch (BeansException ex) {// Explicitly remove instance from singleton cache: It might have been put there// eagerly by the creation process, to allow for circular reference resolution.// Also remove any beans that received a temporary reference to the bean.destroySingleton(beanName);throw ex;}}});//创建这个Beanbean = getObjectForBeanInstance(sharedInstance, name, beanName, mbd);}<span style="white-space:pre"></span>//      这里的实现要比singleton简单,因为不用检查是否已经创建过这个实例else if (mbd.isPrototype()) {// It's a prototype -> create a new instance.Object prototypeInstance = null;try {beforePrototypeCreation(beanName);prototypeInstance = createBean(beanName, mbd, args);}finally {afterPrototypeCreation(beanName);}bean = getObjectForBeanInstance(prototypeInstance, name, beanName, mbd);}else {String scopeName = mbd.getScope();final Scope scope = (Scope) this.scopes.get(scopeName);if (scope == null) {throw new IllegalStateException("No Scope registered for scope '" + scopeName + "'");}try {Object scopedInstance = scope.get(beanName, new ObjectFactory() {//ObjectFactory 是个接口,这里使用模板方法模式public Object getObject() throws BeansException {      beforePrototypeCreation(beanName);try {return createBean(beanName, mbd, args);//这里并未实现这个方法,这是个抽象方法,使用了策略设计模式}finally {afterPrototypeCreation(beanName);}}});bean = getObjectForBeanInstance(scopedInstance, name, beanName, mbd);}catch (IllegalStateException ex) {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",ex);}}}// Check if required type matches the type of the actual bean instance.if (requiredType != null && bean != null && !requiredType.isAssignableFrom(bean.getClass())) {throw new BeanNotOfRequiredTypeException(name, requiredType, bean.getClass());}return bean;}
</pre><p></p><p>这个getSingleton()方法实现了创建单例的过程 ObjectFactory是个接口,这里用到了模板模式,而createBean()这是个抽象方法,所以使用的策略设计模式</p><pre name="code" class="java">


public Object getSingleton(String beanName, ObjectFactory singletonFactory) {Assert.notNull(beanName, "'beanName' must not be null");synchronized (this.singletonObjects) {Object singletonObject = this.singletonObjects.get(beanName);//检查是否已经创建过这个实例,如果是的话直接返回if (singletonObject == null) {if (this.singletonsCurrentlyInDestruction) {throw new BeanCreationNotAllowedException(beanName,"Singleton bean creation not allowed while the singletons of this factory are in destruction " +"(Do not request a bean from a BeanFactory in a destroy method implementation!)");}if (logger.isDebugEnabled()) {logger.debug("Creating shared instance of singleton bean '" + beanName + "'");}//创建前将beanName添加到Set中.beforeSingletonCreation(beanName);boolean recordSuppressedExceptions = (this.suppressedExceptions == null);if (recordSuppressedExceptions) {this.suppressedExceptions = new LinkedHashSet();}try {//  singletonObject = singletonFactory.getObject();}catch (BeanCreationException ex) {if (recordSuppressedExceptions) {for (Iterator it = this.suppressedExceptions.iterator(); it.hasNext();) {ex.addRelatedCause((Exception) it.next());}}throw ex;}finally {if (recordSuppressedExceptions) {this.suppressedExceptions = null;}//从set集合中移除afterSingletonCreation(beanName);}addSingleton(beanName, singletonObject);}return (singletonObject != NULL_OBJECT ? singletonObject : null);}}

最后实现创建Bean的方法是在AbstractAutowireCapableBeanFactory类的createBean()方法中,代码如下:


protected Object createBean(final String beanName, final RootBeanDefinition mbd, final Object[] args)throws BeanCreationException {AccessControlContext acc = AccessController.getContext();//AccessController.doPrivileged()这个方法的作用是不做权限检查return AccessController.doPrivileged(new PrivilegedAction() {public Object run() {if (logger.isDebugEnabled()) {logger.debug("Creating instance of bean '" + beanName + "'");}// Make sure bean class is actually resolved at this point.resolveBeanClass(mbd, beanName);// Prepare method overrides.try {mbd.prepareMethodOverrides();}catch (BeanDefinitionValidationException ex) {throw new BeanDefinitionStoreException(mbd.getResourceDescription(),beanName, "Validation of method overrides failed", ex);}try {// Give BeanPostProcessors a chance to return a proxy instead of the target bean instance.试着返回一个代理Object bean = resolveBeforeInstantiation(beanName, mbd);if (bean != null) {return bean;}}catch (Throwable ex) {throw new BeanCreationException(mbd.getResourceDescription(), beanName,"BeanPostProcessor before instantiation of bean failed", ex);}Object beanInstance = doCreateBean(beanName, mbd, args);//创建实例if (logger.isDebugEnabled()) {logger.debug("Finished creating instance of bean '" + beanName + "'");}return beanInstance;}}, acc);}

doCreateBean方法如下


protected Object doCreateBean(final String beanName, final RootBeanDefinition mbd, final Object[] args) {// Instantiate the bean.BeanWrapper instanceWrapper = null;if (mbd.isSingleton()) {instanceWrapper = (BeanWrapper) this.factoryBeanInstanceCache.remove(beanName);}if (instanceWrapper == null) {instanceWrapper = createBeanInstance(beanName, mbd, args);}final Object bean = (instanceWrapper != null ? instanceWrapper.getWrappedInstance() : null);Class beanType = (instanceWrapper != null ? instanceWrapper.getWrappedClass() : null);// Allow post-processors to modify the merged bean definition.synchronized (mbd.postProcessingLock) {if (!mbd.postProcessed) {applyMergedBeanDefinitionPostProcessors(mbd, beanType, beanName);mbd.postProcessed = true;}}// Eagerly cache singletons to be able to resolve circular references// even when triggered by lifecycle interfaces like BeanFactoryAware.boolean earlySingletonExposure = (mbd.isSingleton() && this.allowCircularReferences &&isSingletonCurrentlyInCreation(beanName));if (earlySingletonExposure) {if (logger.isDebugEnabled()) {logger.debug("Eagerly caching bean '" + beanName +"' to allow for resolving potential circular references");}addSingletonFactory(beanName, new ObjectFactory() {public Object getObject() throws BeansException {return getEarlyBeanReference(beanName, mbd, bean);}});}// Initialize the bean instance.Object exposedObject = bean;try {populateBean(beanName, mbd, instanceWrapper);exposedObject = initializeBean(beanName, exposedObject, mbd);}catch (Throwable ex) {if (ex instanceof BeanCreationException && beanName.equals(((BeanCreationException) ex).getBeanName())) {throw (BeanCreationException) ex;}else {throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Initialization of bean failed", ex);}}if (earlySingletonExposure) {Object earlySingletonReference = getSingleton(beanName, false);if (earlySingletonReference != null) {if (exposedObject == bean) {exposedObject = earlySingletonReference;}else if (!this.allowRawInjectionDespiteWrapping && hasDependentBean(beanName)) {String[] dependentBeans = getDependentBeans(beanName);Set actualDependentBeans = new LinkedHashSet(dependentBeans.length);for (int i = 0; i < dependentBeans.length; i++) {String dependentBean = dependentBeans[i];if (!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.");}}}}// Register bean as disposable.registerDisposableBeanIfNecessary(beanName, bean, mbd);return exposedObject;}

doCreateBean方法暂时不分析









0 0