1. 程式人生 > >Spring原始碼解析-beanfactory

Spring原始碼解析-beanfactory

準備寫幾篇spring原始碼的文章,整理自己看《spring原始碼深度解析》過程,方便後面學習,希望年前完成吧。上次看過一些,不夠深入,這次又看了下,目的:
1. 只關心書中前半部分,spring IOC和AOP核心部分,後半部分暫不關心;
2. 只關注主流程流轉,細節部分了解功能,太細的不管。

spring的版本號3.1的。

Demo

public class MyBeanTest {

    public static void main(String[] args) {
        BeanFactory ctx = new XmlBeanFactory(new ClassPathResource("spring.xml"
)); MyBean testBean = (MyBean)ctx.getBean("testBean"); System.out.println(testBean.getTestStr()); } }
package qbb.spring.bean;

public class MyBean  {

    private String testStr = "testStr";

    public MyBean(){

    }

    public MyBean(String testStr){
        this.testStr = testStr;
    }

    public
String getTestStr() { return testStr; } public void setTestStr(String testStr) { this.testStr = testStr; } }
<?xml version="1.0" encoding="UTF-8"?>
<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" 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">
<bean name="testBean" class="qbb.spring.bean.MyBean" ></bean> </beans>

uml類圖

上次看的時候就畫過這個圖,這次做了細化和調整。

XmlBeanFactory繼承關係

xmlbeanfactory繼承關係

  1. AliasRegistry定義對Alias的簡單增刪改等操作;
  2. SimpleAliasRegistry使用currenthashmap作為快取,並對介面AliasRegisty進行實現;
  3. SingletonBeanRegistry定義對單例的獲取及獲取;
  4. DefaultSingletonBeanRegistry是SingletonBeanRegistry的實現;
  5. FactoryBeanRegistrySupport在DefaultSingletonBeanRegistry基礎上,增加對FactorBean的特殊處理功能;
  6. BeanFactory定義獲取bean及bean的各種屬性;
  7. HierarchicalBeanFactory繼承BeanFactory,增加對parentFactory的支援;
  8. ConfigurableBeanFactory提供配置各種factory的方法;
  9. ListableBeanFactory根據不同條件獲取bean的配置清單;
  10. AutowireCapableBeanFactory提供建立bean,自動注入,初始化已經應用bean後的處理器;
  11. AbstractBeanFactory綜合FactoryBeanRegistrySupport和ConfigurableBeanFactory功能;
  12. ConfigurableListableBeanFactory是BeanFactory的配置清單,指定忽略型別和介面等;
  13. AbstractAutowireCapableBeanFactory綜合AbstractBeanFactory並對介面AutowireCapalbeBeanFactory的實現;
  14. BeanDefinitionRegistry定義對BeanDefinition的curd操作;
  15. DefaultListableBeanFactory綜合所有功能,主要是bean註冊後的處理;
  16. XmlBeanFactory對DefaultListableBeanFactory類進行了擴充套件,主要是從xml文件讀取BeanDefinition,對於註冊以及獲取Bean都是從父類DefaultLisstableBean繼承的方法去實現,與父類的不同就是增加了XmlBeanDefinitionReader型別的reader屬性,在XmlBeanFactory中主要使用reader屬性對資原始檔進行讀取和註冊;

XmlBeanDefinitionReader

XmlBeanDefinitionReader

  1. EnvironmentCapable定義獲取Environment的方法;
  2. BeanDefinitionReader主要定義資原始檔讀取並轉化為BeanDefinition的各種功能;
  3. AbstractBeanDefinitionReader對介面的實現;
  4. ResourceLoader資源載入器,根據給定的資原始檔地址返回對應的Resource;
  5. DocumentLoader資原始檔轉化為Document的功能;
  6. BeanDefinitionDocumentReader讀取Document並註冊BeanFinition的功能;
  7. BeanDefinitionParserDelegate定義解析element的各種方法;

BeanDefinition

BeanDefinition

  1. BeanDefinition配置檔案bean元素在容器的內部表現形式;
  2. ChildBeanDefinition父子bean中的子bean;
  3. GenericBeanDefinition2.5後加入,一站式的服務類;
  4. RootBeanDefinition對應一般性的bean元素標籤,父子bean中的父bean可以用此表示,沒有父bean的bean也使用來表示;

xml解析beanDefinition

BeanFactory ctx = new XmlBeanFactory(new ClassPathResource("spring.xml"));

資原始檔抽象

new ClassPathResource("spring.xml")

spring將外部的資源封裝成內部使用Resource,可以從檔案,class,jar,還有context上下文:

Resource

我這裡使用ClassPathResource載入spring檔案,當然也可以使用FileSystemResource從檔案系統路徑載入。

loadBeanDefinition

new XmlBeanFactory(new ClassPathResource("spring.xml"));

呼叫XmlBeanFactory構造

// XmlBeanFactory
public XmlBeanFactory(Resource resource) throws BeansException {
    this(resource, null);
}

public XmlBeanFactory(Resource resource, BeanFactory parentBeanFactory) throws BeansException {
    super(parentBeanFactory);
    this.reader.loadBeanDefinitions(resource);
}

在條用super的時候會設定parentBeanFactory,好像只要mvc的時候才看到設定,其他地方基本沒用到。

//AbstractAutowireCapableBeanFactory
public AbstractAutowireCapableBeanFactory(BeanFactory parentBeanFactory) {
    this();
    setParentBeanFactory(parentBeanFactory);
}

public AbstractAutowireCapableBeanFactory() {
    super();
    //忽略一些依賴,在getbean的時候,在例項化屬性填充後,會檢查設定這些依賴關係,
    //然後再去呼叫實現InitializingBean的afterPropertiesSet方法和自定義的Init-Method
    ignoreDependencyInterface(BeanNameAware.class);
    ignoreDependencyInterface(BeanFactoryAware.class);
    ignoreDependencyInterface(BeanClassLoaderAware.class);
}

//AbstractBeanFactory
public void setParentBeanFactory(BeanFactory parentBeanFactory) {
    if (this.parentBeanFactory != null && this.parentBeanFactory != parentBeanFactory) {
        throw new IllegalStateException("Already associated with parent BeanFactory: " + this.parentBeanFactory);
    }
    this.parentBeanFactory = parentBeanFactory;
}

在這些完了後會呼叫

//xmlbeanfactory
this.reader.loadBeanDefinitions(resource);

XmlBeanFactory使用XmlBeanDefinitionReader來解析和註冊bean定義。

//XmlBeanDefinitionReader
public int loadBeanDefinitions(Resource resource) throws BeanDefinitionStoreException {
    //EncodedResource做了編碼處理,getReader時如果有編碼就使用,沒有就不適用
    return loadBeanDefinitions(new EncodedResource(resource));
}

public int loadBeanDefinitions(EncodedResource encodedResource) throws BeanDefinitionStoreException {
    ...
    try {
        InputStream inputStream = encodedResource.getResource().getInputStream();
        try {
            InputSource inputSource = new InputSource(inputStream);
            if (encodedResource.getEncoding() != null) {
                inputSource.setEncoding(encodedResource.getEncoding());
            }
            return doLoadBeanDefinitions(inputSource, encodedResource.getResource());
        }
        finally {
            inputStream.close();
        }
    }
    ...
}

看了下,spring中習慣doXXX來表示真正幹活的程式碼,XXX來做主流程控制。自己寫程式碼的時候有時流程會不清晰,會亂,後來還是從spring裡面學會這招,先提煉主流程,然後再分配。

//XmlBeanDefinitionReader
protected int doLoadBeanDefinitions(InputSource inputSource, Resource resource)
            throws BeanDefinitionStoreException {
    try {
        int validationMode = getValidationModeForResource(resource);
        Document doc = this.documentLoader.loadDocument(
                inputSource, getEntityResolver(), this.errorHandler, validationMode, isNamespaceAware());
        return registerBeanDefinitions(doc, resource);
    }
    ...
}

xml檔案校驗和解析

//XmlBeanDefinitionReader
int validationMode = getValidationModeForResource(resource);
        Document doc = this.documentLoader.loadDocument(
                inputSource, getEntityResolver(), this.errorHandler, validationMode, isNamespaceAware());

xml文件的2種校驗方式:DTD和XSD,通過getValidationModeForResource來獲取,DTD的會包含DOCTYPE,所以通過解析這個是否存在判斷。校驗過後就是通過DefaultDocumentLoader將xml檔案解析Document,xml檔案解析一般就是SAX、Dom、jdom,dom4j。

registerBeanDefinitions

//XmlBeanDefinitionReader
public int registerBeanDefinitions(Document doc, Resource resource) throws BeanDefinitionStoreException {
    //將DefaultBeanDefinitionDocumentReader轉為BeanDefinitionDocumentReader
    BeanDefinitionDocumentReader documentReader = createBeanDefinitionDocumentReader();
    //this.getEnvironment()獲取到的是StandardEnvironment,可以用來獲取系統變數和環境變數
    documentReader.setEnvironment(this.getEnvironment());
    int countBefore = getRegistry().getBeanDefinitionCount();
    //使用DefaultBeanDefinitionDocumentReader解析document
    documentReader.registerBeanDefinitions(doc, createReaderContext(resource));
    return getRegistry().getBeanDefinitionCount() - countBefore;
}

protected XmlReaderContext createReaderContext(Resource resource) {
    if (this.namespaceHandlerResolver == null) {
        //DefaultNamespaceHandlerResolver,主要用來獲取標籤的解析,
        //特別是自定義標籤的解析,後面單獨講下這個,裡面最重要的方法NamespaceHandler resolve(String namespaceUri)
        this.namespaceHandlerResolver = createDefaultNamespaceHandlerResolver();
    }
    return new XmlReaderContext(resource, this.problemReporter, this.eventListener,
            this.sourceExtractor, this, this.namespaceHandlerResolver);
}

最終還是委託DefaultBeanDefinitionDocumentReader來解析Document。

//DefaultBeanDefinitionDocumentReader
public void registerBeanDefinitions(Document doc, XmlReaderContext readerContext) {
    this.readerContext = readerContext;

    logger.debug("Loading bean definitions");
    Element root = doc.getDocumentElement();

    doRegisterBeanDefinitions(root);
}

protected void doRegisterBeanDefinitions(Element root) {
    //profile屬性,類似maven -p,可以定義不同環境下的bean定義,配合環境變數spring.profiles.active使用
    String profileSpec = root.getAttribute(PROFILE_ATTRIBUTE);
    if (StringUtils.hasText(profileSpec)) {
        Assert.state(this.environment != null, "environment property must not be null");
        String[] specifiedProfiles = StringUtils.tokenizeToStringArray(profileSpec, BeanDefinitionParserDelegate.MULTI_VALUE_ATTRIBUTE_DELIMITERS);
        if (!this.environment.acceptsProfiles(specifiedProfiles)) {
            return;
        }
    }

    // any nested <beans> elements will cause recursion in this method. In
    // order to propagate and preserve <beans> default-* attributes correctly,
    // keep track of the current (parent) delegate, which may be null. Create
    // the new (child) delegate with a reference to the parent for fallback purposes,
    // then ultimately reset this.delegate back to its original (parent) reference.
    // this behavior emulates a stack of delegates without actually necessitating one.
    BeanDefinitionParserDelegate parent = this.delegate;
    // BeanDefinitionParserDelegate
    this.delegate = createHelper(readerContext, root, parent);

    preProcessXml(root); //子類實現
    parseBeanDefinitions(root, this.delegate);
    postProcessXml(root); //子類實現

    this.delegate = parent;
}

protected BeanDefinitionParserDelegate createHelper(XmlReaderContext readerContext, Element root, BeanDefinitionParserDelegate parentDelegate) {
    BeanDefinitionParserDelegate delegate = new BeanDefinitionParserDelegate(readerContext, environment);
    delegate.initDefaults(root, parentDelegate);
    return delegate;
}

//BeanDefinitionParserDelegate
public void initDefaults(Element root, BeanDefinitionParserDelegate parent) {
    populateDefaults(this.defaults, (parent != null ? parent.defaults : null), root);
    this.readerContext.fireDefaultsRegistered(this.defaults);
}

//收集一些預設屬性
protected void populateDefaults(DocumentDefaultsDefinition defaults, DocumentDefaultsDefinition parentDefaults, Element root) {
    String lazyInit = root.getAttribute(DEFAULT_LAZY_INIT_ATTRIBUTE);
    if (DEFAULT_VALUE.equals(lazyInit)) {
        lazyInit = parentDefaults != null ? parentDefaults.getLazyInit() : FALSE_VALUE;
    }
    defaults.setLazyInit(lazyInit);

    String merge = root.getAttribute(DEFAULT_MERGE_ATTRIBUTE);
    if (DEFAULT_VALUE.equals(merge)) {
        merge = parentDefaults != null ? parentDefaults.getMerge() : FALSE_VALUE;
    }
    defaults.setMerge(merge);

    String autowire = root.getAttribute(DEFAULT_AUTOWIRE_ATTRIBUTE);
    if (DEFAULT_VALUE.equals(autowire)) {
        autowire = parentDefaults != null ? parentDefaults.getAutowire() : AUTOWIRE_NO_VALUE;
    }
    defaults.setAutowire(autowire);

    // don't fall back to parentDefaults for dependency-check as it's no
    // longer supported in <beans> as of 3.0. Therefore, no nested <beans>
    // would ever need to fall back to it.
    defaults.setDependencyCheck(root.getAttribute(DEFAULT_DEPENDENCY_CHECK_ATTRIBUTE));

    if (root.hasAttribute(DEFAULT_AUTOWIRE_CANDIDATES_ATTRIBUTE)) {
        defaults.setAutowireCandidates(root.getAttribute(DEFAULT_AUTOWIRE_CANDIDATES_ATTRIBUTE));
    }
    else if (parentDefaults != null) {
        defaults.setAutowireCandidates(parentDefaults.getAutowireCandidates());
    }

    if (root.hasAttribute(DEFAULT_INIT_METHOD_ATTRIBUTE)) {
        defaults.setInitMethod(root.getAttribute(DEFAULT_INIT_METHOD_ATTRIBUTE));
    }
    else if (parentDefaults != null) {
        defaults.setInitMethod(parentDefaults.getInitMethod());
    }

    if (root.hasAttribute(DEFAULT_DESTROY_METHOD_ATTRIBUTE)) {
        defaults.setDestroyMethod(root.getAttribute(DEFAULT_DESTROY_METHOD_ATTRIBUTE));
    }
    else if (parentDefaults != null) {
        defaults.setDestroyMethod(parentDefaults.getDestroyMethod());
    }

    defaults.setSource(this.readerContext.extractSource(root));
}

parseBeanDefinitions

//DefaultBeanDefinitionDocumentReader
protected void parseBeanDefinitions(Element root, BeanDefinitionParserDelegate delegate) {
    //預設是bean
    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)) {
                    //解析預設bean定義
                    parseDefaultElement(ele, delegate);
                }
                else {
                    //自定義
                    delegate.parseCustomElement(ele);
                }
            }
        }
    }
    else {
        //自定義
        delegate.parseCustomElement(root);
    }
}

private void parseDefaultElement(Element ele, BeanDefinitionParserDelegate delegate) {
    //import
    if (delegate.nodeNameEquals(ele, IMPORT_ELEMENT)) {
        importBeanDefinitionResource(ele);
    }
    //別名
    else if (delegate.nodeNameEquals(ele, ALIAS_ELEMENT)) {
        processAliasRegistration(ele);
    }
    //bean
    else if (delegate.nodeNameEquals(ele, BEAN_ELEMENT)) {
        processBeanDefinition(ele, delegate);
    }
    //beans裡面巢狀的bean解析
    else if (delegate.nodeNameEquals(ele, NESTED_BEANS_ELEMENT)) {
        // recurse
        doRegisterBeanDefinitions(ele);
    }
}

//BeanDefinitionParserDelegate
public boolean isDefaultNamespace(String namespaceUri) {
    //BEANS_NAMESPACE_URI = "http://www.springframework.org/schema/beans";
    return (!StringUtils.hasLength(namespaceUri) || BEANS_NAMESPACE_URI.equals(namespaceUri));
}

public boolean isDefaultNamespace(Node node) {
    return isDefaultNamespace(getNamespaceURI(node));
}

可以看到這裡的Document解析節點是先校驗是否為預設bean的namespace,是的話就判斷節點是import、alias、bean,不是就按照自定義namespace方式解析。

對於import的解析時迴圈解析import的Resource檔案,alias是註冊別名到map(會校驗是否存在別名的迴圈定義),最核心的還是bean的解析。

processBeanDefinition

//DefaultBeanDefinitionDocumentReader
protected void processBeanDefinition(Element ele, BeanDefinitionParserDelegate delegate) {
    //委託DefaultBeanDefinitionDocumentReader完成bean解析,最終bdHolder持有beanDefinition和beanName,別名
    BeanDefinitionHolder bdHolder = delegate.parseBeanDefinitionElement(ele);
    if (bdHolder != null) {
        //是否有自定義屬性需要處理
        bdHolder = delegate.decorateBeanDefinitionIfRequired(ele, bdHolder);
        try {
            // Register the final decorated instance.
            BeanDefinitionReaderUtils.registerBeanDefinition(bdHolder, getReaderContext().getRegistry());
        }
        catch (BeanDefinitionStoreException ex) {
            getReaderContext().error("Failed to register bean definition with name '" +
                    bdHolder.getBeanName() + "'", ele, ex);
        }
        // Send registration event.
        getReaderContext().fireComponentRegistered(new BeanComponentDefinition(bdHolder));
    }
}

//註冊beanDefinition和別名
public static void registerBeanDefinition(
        BeanDefinitionHolder definitionHolder, BeanDefinitionRegistry registry)
        throws BeanDefinitionStoreException {

    // Register bean definition under primary name.
    String beanName = definitionHolder.getBeanName();
    registry.registerBeanDefinition(beanName, definitionHolder.getBeanDefinition());

    // Register aliases for bean name, if any.
    String[] aliases = definitionHolder.getAliases();
    if (aliases != null) {
        for (String aliase : aliases) {
            registry.registerAlias(beanName, aliase);
        }
    }
}

delegate-parseBeanDefinitionElement(ele)

//BeanDefinitionParserDelegate
public BeanDefinitionHolder parseBeanDefinitionElement(Element ele) {
    return parseBeanDefinitionElement(ele, null);
}

public BeanDefinitionHolder parseBeanDefinitionElement(Element ele, BeanDefinition containingBean) {
    //bean的id和name屬性
    String id = ele.getAttribute(ID_ATTRIBUTE);
    String nameAttr = ele.getAttribute(NAME_ATTRIBUTE);

    //name多個的情況,放入別名
    List<String> aliases = new ArrayList<String>();
    if (StringUtils.hasLength(nameAttr)) {
        String[] nameArr = StringUtils.tokenizeToStringArray(nameAttr, MULTI_VALUE_ATTRIBUTE_DELIMITERS);
        aliases.addAll(Arrays.asList(nameArr));
    }

    String beanName = id;
    if (!StringUtils.hasText(beanName) && !aliases.isEmpty()) {
        beanName = aliases.remove(0);
        if (logger.isDebugEnabled()) {
            logger.debug("No XML 'id' specified - using '" + beanName +
                    "' as bean name and " + aliases + " as aliases");
        }
    }

    if (containingBean == null) {
        //檢查名稱是否用過,會有Set儲存用過的名稱
        checkNameUniqueness(beanName, aliases, ele);
    }

    //解析bean的element成最終的beanDefinition
    AbstractBeanDefinition beanDefinition = parseBeanDefinitionElement(ele, beanName, containingBean);
    if (beanDefinition != null) {
        //名稱不存在就spring生成一個
        if (!StringUtils.hasText(beanName)) {
            try {
                if (containingBean != null) {
                    beanName = BeanDefinitionReaderUtils.generateBeanName(
                            beanDefinition, this.readerContext.getRegistry(), true);
                }
                else {
                    beanName = this.readerContext.generateBeanName(beanDefinition);
                    // Register an alias for the plain bean class name, if still possible,
                    // if the generator returned the class name plus a suffix.
                    // This is expected for Spring 1.2/2.0 backwards compatibility.
                    String beanClassName = beanDefinition.getBeanClassName();
                    if (beanClassName != null &&
                            beanName.startsWith(beanClassName) && beanName.length() > beanClassName.length() &&
                            !this.readerContext.getRegistry().isBeanNameInUse(beanClassName)) {
                        aliases.add(beanClassName);
                    }
                }
                if (logger.isDebugEnabled()) {
                    logger.debug("Neither XML 'id' nor 'name' specified - " +
                            "using generated bean name [" + beanName + "]");
                }
            }
            catch (Exception ex) {
                error(ex.getMessage(), ele);
                return null;
            }
        }
        String[] aliasesArray = StringUtils.toStringArray(aliases);
        //返回一個BeanDefinitionHolder持有bean定義,beanname和別名陣列
        return new BeanDefinitionHolder(beanDefinition, beanName, aliasesArray);
    }

    return null;
}

//最核心的方法:完成bean定義的element的元素解析
public AbstractBeanDefinition parseBeanDefinitionElement(
        Element ele, String beanName, BeanDefinition containingBean) {

    this.parseState.push(new BeanEntry(beanName));

    String className = null;
    if (ele.hasAttribute(CLASS_ATTRIBUTE)) {
        className = ele.getAttribute(CLASS_ATTRIBUTE).trim();
    }

    try {
        String parent = null;
        if (ele.hasAttribute(PARENT_ATTRIBUTE)) {
            parent = ele.getAttribute(PARENT_ATTRIBUTE);
        }
        //建立GenericBeanDefinition並設定beanclass或beanclassname
        AbstractBeanDefinition bd = createBeanDefinition(className, parent);
        //bean的屬性收集,如scope,inti-method,factory-method,注入方式、依賴等
        parseBeanDefinitionAttributes(ele, beanName, containingBean, bd);
        //提取description
        bd.setDescription(DomUtils.getChildElementValueByTagName(ele, DESCRIPTION_ELEMENT));
        //提取meta
        parseMetaElements(ele, bd);
        //處理override-mthod和replace-method子元素
        parseLookupOverrideSubElements(ele, bd.getMethodOverrides());
        parseReplacedMethodSubElements(ele, bd.getMethodOverrides());
        //處理構造注入元素
        parseConstructorArgElements(ele, bd);
        //處理屬性注入
        parsePropertyElements(ele, bd);
        //qualifier提取,@Qualifier註解的xml配置方式
        parseQualifierElements(ele, bd);

        bd.setResource(this.readerContext.getResource());
        bd.setSource(extractSource(ele));

        return bd;
    }
    ...
}

到這裡完成spring檔案的bean解析和註冊。

bean獲取

getBean

//AbstractBeanFactory
public Object getBean(String name) throws BeansException {
    return doGetBean(name, null, null, false);
}

protected <T> T doGetBean(
        final String name, final Class<T> requiredType, final Object[] args, boolean typeCheckOnly)
        throws BeansException {
    //轉換beanName,存在name為別名或者factorybean的name的情況,
    //如果為factoryBean,你可能想獲取的是factorybean本身,也可能是factorybean的getObject返回的真實bean
    final String beanName = transformedBeanName(name);
    Object bean;

    // Eagerly check singleton cache for manually registered singletons.
    // 從快取獲取下
    Object sharedInstance = getSingleton(beanName);
    if (sharedInstance != null && args == 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 + "'");
            }
        }
        //getObjectForBeanInstance在獲取bean後都會呼叫,主要處理factorybean情況還有後處理器
        bean = getObjectForBeanInstance(sharedInstance, name, beanName, null);
    }

    else {
        // Fail if we're already creating this bean instance:
        // We're assumably within a circular reference.
        // spring解決不了scope為prototype的bean迴圈依賴,丟擲異常
        // spring只能解決Singleton的屬性注入情況下迴圈依賴
        if (isPrototypeCurrentlyInCreation(beanName)) {
            throw new BeanCurrentlyInCreationException(beanName);
        }

        // Check if bean definition exists in this factory.
        BeanFactory parentBeanFactory = getParentBeanFactory();
        //如果parentbeanfactory存在並且當前beanfactory不包含,那就從parent獲取
        if (parentBeanFactory != null && !containsBeanDefinition(beanName)) {
            // Not found -> check parent.
            String nameToLookup = originalBeanName(name);
            if (args != null) {
                // Delegation to parent with explicit args.
                return (T) parentBeanFactory.getBean(nameToLookup, args);
            }
            else {
                // No args -> delegate to standard getBean method.
                return parentBeanFactory.getBean(nameToLookup, requiredType);
            }
        }

        if (!typeCheckOnly) {
            markBeanAsCreated(beanName);
        }

        //之前的GenericBeanDefinition轉為RootBeanDefinition,涉及到父子bean的合併處理
        final RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);
        //校驗mbd不為抽象,如果getbean給定引數的話,mbd必須為prototype
        checkMergedBeanDefinition(mbd, beanName, args);

        // Guarantee initialization of beans that the current bean depends on.
        // 依賴bean先處理
        String[] dependsOn = mbd.getDependsOn();
        if (dependsOn != null) {
            for (String dependsOnBean : dependsOn) {
                getBean(dependsOnBean);
                registerDependentBean(dependsOnBean, beanName);
            }
        }

        // Create bean instance.
        // 單例bean的建立
        if (mbd.isSingleton()) {
            sharedInstance = getSingleton(beanName, new ObjectFactory<Object>() {
                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;
                    }
                }
            });
            bean = getObjectForBeanInstance(sharedInstance, name, beanName, mbd);
        }

        else if (mbd.isPrototype()) {
            //prototypebean建立
            // 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 {
            //指定scope的bean建立,還沒過這種
            String scopeName = mbd.getScope();
            final 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<Object>() {
                    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);
            }
        }
    }

    // getbean指定型別,需要校驗和轉換
    if (requiredType != null && bean != null && !requiredType.isAssignableFrom(bean.getClass())) {
        try {
            return getTypeConverter().convertIfNecessary(bean, requiredType);
        }
        catch (TypeMismatchException ex) {
            if (logger.isDebugEnabled()) {
                logger.debug("Failed to convert bean '" + name + "' to required type [" +
                        ClassUtils.getQualifiedName(requiredType) + "]", ex);
            }
            throw new BeanNotOfRequiredTypeException(name, requiredType, bean.getClass());
        }
    }
    return (T) bean;
}

裡面最需要關心的幾個處理:

  1. 從快取獲取beanInstance:getSingleton(beanName)
  2. 獲取bean後的處理:getObjectForBeanInstance(sharedInstance, name, beanName, null);
  3. 單例bean建立:getSingleton中createBean方法;

Object sharedInstance = getSingleton(beanName)

//DefaultSingletonBeanRegistry
protected Object getSingleton(String beanName, boolean allowEarlyReference) {
    Object singletonObject = this.singletonObjects.get(beanName);
    if (singletonObject == null) {
        synchronized (this.singletonObjects) {
            singletonObject = this.earlySingletonObjects.get(beanName);
            if (singletonObject == null && allowEarlyReference) {
                ObjectFactory singletonFactory = this.singletonFactories.get(beanName);
                if (singletonFactory != null) {
                    singletonObject = singletonFactory.getObject();
                    this.earlySingletonObjects.put(beanName, singletonObject);
                    this.singletonFactories.remove(beanName);
                }
            }
        }
    }
    return (singletonObject != NULL_OBJECT ? singletonObject : null);
}
  1. singletonObjects:beanName和建立bean例項之前關係;
  2. earlySingletonObjects:beanName和建立bean例項之前關係,此時可以通過getBean獲取到,主要是為了解決迴圈依賴;
  3. singletonFactories:beanName和建立bean的factory的關係,提前暴露建立bean的factory;
  4. registeredSingletons:已經註冊的beanName。

singleton的getSingleton建立

//AbstractBeanFactory
sharedInstance = getSingleton(beanName, new ObjectFactory<Object>() {
    public Object getObject() throws BeansException {
        try {
            return createBean(beanName, mbd, args);
        }
        catch (BeansException ex) {
            ...
        }
    }
});

//DefaultSingletonBeanRegistry
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 + "'");
            }
            //加到singletonsCurrentlyInCreation
            beforeSingletonCreation(beanName);
            boolean recordSuppressedExceptions = (this.suppressedExceptions == null);
            if (recordSuppressedExceptions) {
                this.suppressedExceptions = new LinkedHashSet<Exception>();
            }
            try {
                //呼叫objectfactory的getObject方法的createBean
                singletonObject = singletonFactory.getObject();
            }
            catch (BeanCreationException ex) {
                if (recordSuppressedExceptions) {
                    for (Exception suppressedException : this.suppressedExceptions) {
                        ex.addRelatedCause(suppressedException);
                    }
                }
                throw ex;
            }
            finally {
                if (recordSuppressedExceptions) {
                    this.suppressedExceptions = null;
                }
                //從singletonsCurrentlyInCreation移除
                afterSingletonCreation(beanName);
            }
            //
            addSingleton(beanName, singletonObject);
        }
        return (singletonObject != NULL_OBJECT ? singletonObject : null);
    }
}

//加入singletonObjects和registeredSingletons
protected void addSingleton(String beanName, Object singletonObject) {
    synchronized (this.singletonObjects) {
        this.singletonObjects.put(beanName, (singletonObject != null ? singletonObject : NULL_OBJECT));
        this.singletonFactories.remove(beanName);
        this.earlySingletonObjects.remove(beanName);
        this.registeredSingletons.add(beanName);
    }
}

控制createBean建立的主流程

createbean的主流程

//AbstractAutowireCapableBeanFactory
//核心建立bean
@Override
protected Object createBean(final String beanName, final RootBeanDefinition mbd, final Object[] args)
        throws BeanCreationException {

    if (logger.isDebugEnabled()) {
        logger.debug("Creating instance of bean '" + beanName + "'");
    }
    // beanDefinition的beanclass存在,之前beanDefinition會根據classloader是否存在,來儲存clas,
    // 這裡,如果beanclass存在就返回,不存在就通過class.forname來載入beanclassname
    resolveBeanClass(mbd, beanName);

    // Prepare method overrides.
    try {
        // 預判override-method和replace-method方法是否過載,只是提前判斷下,不處理
        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.
        // 呼叫例項化前處理器方法,可以在這裡切入代理,提前返回代理bean,
        // 如果使用自定義的TargetSource,會在這裡走aop,否則是在處理後處理器呼叫走aop
        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);
    }
    //建立bean例項
    Object beanInstance = doCreateBean(beanName, mbd, args);
    if (logger.isDebugEnabled()) {
        logger.debug("Finished creating instance of bean '" + beanName + "'");
    }
    return beanInstance;
}

//利用InstantiationAwareBeanPostProcessor的postProcessBeforeInstantiation提前建立bean例項
protected Object resolveBeforeInstantiation(String beanName, RootBeanDefinition mbd) {
    Object bean = null;
    if (!Boolean.FALSE.equals(mbd.beforeInstantiationResolved)) {
        // Make sure bean class is actually resolved at this point.
        if (mbd.hasBeanClass() && !mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
            bean = applyBeanPostProcessorsBeforeInstantiation(mbd.getBeanClass(), beanName);
            if (bean != null) {
                //應用初始化後方法
                bean = applyBeanPostProcessorsAfterInitialization(bean, beanName);
            }
        }
        mbd.beforeInstantiationResolved = (bean != null);
    }
    return bean;
}

//postProcessBeforeInstantiation
protected Object applyBeanPostProcessorsBeforeInstantiation(Class beanClass, String beanName)
        throws BeansException {

    for (BeanPostProcessor bp : getBeanPostProcessors()) {
        if (bp instanceof InstantiationAwareBeanPostProcessor) {
            InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
            Object result = ibp.postProcessBeforeInstantiation(beanClass, beanName);
            if (result != null) {
                return result;
            }
        }
    }
    return null;
}

真正幹活的doCreateBean

//AbstractAutowireCapableBeanFactory
protected Object doCreateBean(final String beanName, final RootBeanDefinition mbd, final Object[] args) {
    // Instantiate the bean.
    BeanWrapper instanceWrapper = null;
    if (mbd.isSingleton()) {
        instanceWrapper = this.factoryBeanInstanceCache.remove(beanName);
    }
    if (instanceWrapper == null) {
        //例項化bean
        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) {
            //書裡面說會在這裡處理@autowire註解,不過沒測試這種情況,這裡todo下
            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,加入後,如果其他bean,需要當前bean例項填充屬性,就可以從objectFactory中getObject獲取到
        addSingletonFactory(beanName, new ObjectFactory() {
            public Object getObject() throws BeansException {