1. 程式人生 > >spring原始碼分析系列3:BeanFactory核心容器的研究

spring原始碼分析系列3:BeanFactory核心容器的研究

目錄

@(spring原始碼分析系列3:核心容器的研究)
在講容器之前,再明確一下知識點。

  • BeanDefinition是Bean在容器的描述。BeanDefinition與Bean不是一個東西。
  • Bean是根據BeanDefinition創建出來的。也即是我們所說的物件。

BeanDefinition物料需要有地方儲存,Bean成品需要有地方存。今天我們講講倉庫。

BeanFactory家族


此圖是預設容器DefaultListableBeanFactory的繼承,實現關係圖.我們從右向左來分析下.

  1. BeanFactory介面:
    容器頂級介面,提供了容器最基本的能力,包括獲取bean,是否包含bean,是否單例,獲取bean型別,Bean的別名等方法。
  2. ListableBeanFactory介面:
    BeanFactory的子介面;具有批量獲取Bean的能力
  3. HierarchicalBeanFactory介面:具有訪問父容器的能力。有層次的BeanFactory。
  4. AutowireCapableBeanFactory介面:繼承BeanFactory,擴充套件了自動裝配能力。這個介面更多的作用是用於於與其他框架整合,把不在spring容器中的Bean加入到Spring容器生命週期管理中來。此介面很少用
  5. ConfigurableBeanFactory:定義了BeanFactory的配置。繼承HierarchicalBeanFactory和SingletonBeanRegistry介面。實現了此介面的容器,具有層次,單例BeanDefinition註冊功能。
  6. ConfigurableListableBeanFactory:
    大融合介面,除了具有上述介面的能外,還具有:類載入器,型別轉化,屬性編輯器,BeanPostProcessor,作用域,bean定義,處理bean依賴關係, bean銷燬等功能。

  7. SingletonBeanRegistry介面: 具有Bean的操作能力.註冊,查詢,獲取Bean數量等能力. 注意此處的Bean是例項.區別於BeanDefinition.

  8. SimpleAliasRegistry:Bean的別名操作類,實現了AliasRegistry.具有儲存Bean別名,註冊Bean別名,獲取Bean別名的功能.aliasMap屬性儲存Bean別名

  9. DefaultSingletonBeanRegistry:除了繼承了SimpleAliasRegistry的功能外. 最重要的是實現了SingletonBeanRegistry介面.具有儲存Bean例項,註冊Bean,獲取Bean的能力.我們定義的被Spring管理的Class類的例項物件,以及例項的之間的相互依賴關係都是儲存在此類中.預設常用的容器DefaultListableBeanFactory的Bean的相關能力.就是通過間接繼承此類來實現的.
    /** Disposable bean instances: bean name --> disposable instance */
    private final Map<String, Object> disposableBeans = new LinkedHashMap<String, Object>();

    /** Map between containing bean names: bean name --> Set of bean names that the bean contains */
    private final Map<String, Set<String>> containedBeanMap = new ConcurrentHashMap<String, Set<String>>(16);

    /** Map between dependent bean names: bean name --> Set of dependent bean names */
    private final Map<String, Set<String>> dependentBeanMap = new ConcurrentHashMap<String, Set<String>>(64);

    /** Map between depending bean names: bean name --> Set of bean names for the bean's dependencies */
    private final Map<String, Set<String>> dependenciesForBeanMap = new ConcurrentHashMap<String, Set<String>>(64)
  1. FactoryBeanRegistrySupport: 提供多工廠Bean的支援.FactoryBean通過其名字我也可以看出是生產Bean的Bean.
  2. AbstractBeanFactory抽象類: 承上啟下.從圖中我們看出. AbstractBeanFactory.通過繼承關係,繼承FactoryBeanRegistrySupport各種能力.而且實現了右邊部分介面.已然是比較完備的Bean容器了.AbstractBeanFactory還通過模板模式定義了獲取Bean的演算法骨架,
  3. AbstractAutowireCapableBeanFactory: .具有大部分的能力. 實現了AbstractBeanFactory定義的模板方法.其中doCreateBean方法邏輯是把一個BeanDefinition變成Bean的過程.這個方法非常重要.通常我們使用類建立物件.直接new出來. spring把BeanDefinition到Bean的過程模板化,留下了很多擴充套件點. 留給使用者可以在不同的時刻自定義BeanDefition建立Bean的過程.
  4. DefaultListableBeanFactory常用的預設容器實現,也是spring最常使用的容器類.看左邊DefaultListableBeanFactory實現了BeanDefinitionRegistry介面. 這說明什麼?說明DefaultListableBeanFactory具有儲存BeanDefinition,操作BeanDefinition的能力.DefaultListableBeanFactory通過繼承關係也具有了Bean的儲存操作功能.

小結:

  1. BeanFactory體系,介面分明,完美的體現了介面分離原則。
  2. BeanFactory體系中有兩種儲存,一種是BeanDefinition的儲存,另一個是Bean的儲存.
  3. DefaultListableBeanFactory作為最常用的容器類.不但具有BeanDefinition的儲存操作功能,而且通過繼承具有Bean的儲存操作功能.DefaultListableBeanFactory把儲存的BeanDefinition通過一定演算法建立Bean並存儲起來.

BeanDefinition,BeanFactory,Bean三者關係

通過上面的對各個介面,類的認識.我們再來看看三者的關係.

我們向BeanFactory容器中注入一個BeanDefinition。BeanFactory幫我們儲存起來.當我們想要得到一個Bean時.BeanFactory 幫我們把BeanDefinition建立Bean.並快取起來.這個建立過程是可參與的.

  • BeanFactory儲存了BeanDefiniton與Bean.
  • BeanFactory具有使用BeanDefinition建立Bean的功能
  • BeanFactory允許使用者可以干預BeanDefinition生成Bean的功能.

BeanFactory中的擴充套件點

設計原則之開閉原則說的特別好:說一個軟體實體應該通過擴充套件來實現變化.
很多優秀的框架都有類似的擴充套件點設計,列如:

  • Tomcat中的Filter
  • Tomcat中的pipline-valve
  • springmvc中的Interceptor

BeanFactory中從BeanDefinition到Bean並不是一下子就完成的.這有一個過程.spring正是在這個過程中留下擴充套件點.來實現BeanDefinition到Bean的過程中的各種自定義變化.

從上面我們得知:AbstractAutowireCapableBeanFactory中有個doCreateBean()正是BeanDefinition到Bean的建立方法.接下來我們看看這個方法.有哪些擴充套件點:

  1. xxxAware介面:使Bean可以獲得xxx. 列如實現了BeanFactoryAware介面的類,可以在該Bean被載入的過程中獲取載入該Bean的BeanFactory
  2. BeanPostProcessor:BeanPostProcessor介面定義的兩個方法,分別在bean的初始化方法(InitializingBean介面,或者init-method定義)執行的前後執行
  3. InitializingBean介面: 實現了InitializingBean介面的類,執行afterPropertiesSet
  4. 自定義的init-method方法:

總結:

BeanFactory是物料與成品倉庫,並配生產線,把BeanDefinition生產成Bean 。BeanFactory留下很多擴充套件點, 方便開發人員可以參與BeanDefinition到Bean的建立過程.

歡迎大家關注我的公眾號【原始碼行動】,最新個人理解及時奉送。

相關推薦

spring原始碼分析系列3:BeanFactory核心容器研究

目錄 @(spring原始碼分析系列3:核心容器的研究) 在講容器之前,再明確一下知識點。 BeanDefinition是Bean在容器的描述。BeanDefinition與Bean不是一個東西。 Bean是根據BeanDefinition創建出來的。也即是

spring原始碼分析系列 (2) spring拓展介面BeanPostProcessor

主要分析內容: 一、BeanPostProcessor簡述與demo示例 二、BeanPostProcessor原始碼分析:註冊時機和觸發點   一、BeanPostProcessor簡述與demo示例 BeanPostProcessor是spring非常重要的拓展介面,例如aop通過拓展

Spring原始碼分析】11-BeanFactory

BeanFactory是Spring容器實現的基礎,訪問Spring容器的根介面。每個bean都是通過string型別bean name進行標識.這邊提供了設計模式單例,原型的替代實現。如果bean name配置為單例,應用內只會獲取到一個例項。如果配置為原型,那麼可以例項化

Spring原始碼分析系列】ApplicationContext 相關介面架構分析

在使用Spring的時候,我們經常需要先得到一個ApplicationContext物件,然後從該物件中獲取我們配置的Bean物件

spring原始碼分析系列2:Bean與BeanDefinition關係

介面表示一種能力,實現了一個介面,即擁有一種能力。 BeanDefinition與Bean的關係, 就好比類與物件的關係. 類在spring的資料結構就是BeanDefinition.根據BeanDefinition得到的物件就是我們需要的Bean. 我認為理解Bean與BeanDefinition是理解

spring原始碼分析系列4:ApplicationContext研究

ApplicationContext介面 首先看一下一個最基本的上下文應該是什麼樣子 ApplicationContext介面的註釋裡寫的很清楚: 一個基本applicationContext應該提供: 訪問Bean的能力 提供載入資源的能力 釋出事件的能力 解析訊息、支援國際化的能力 Abstrac

spring原始碼分析系列5:ApplicationContext的初始化與Bean生命週期

回顧Bean與BeanDefinition的關係. BeanFactory容器. ApplicationContext上下文. 首先總結下: 開發人員定義Bean資訊:分為XML形式定義;註解式定義 ApplicationContext蒐集Bean的定義;儲存到BeabFactory容器的中。 BeanFa

Spring原始碼分析(二)(IoC容器的實現)(3

BeanDefinition的載入和解析     這個載入過程,相當於把定義的BeanDefinition在IoC容器中轉化成一個Spring內部表示的資料結構的過程。IoC容器對Bean的管理和依賴注入功能的實現,是通過對其持有的BeanDefinition進

Spring 原始碼分析(二) —— 核心容器

容器概述       IoC也被稱作依賴注入(DI)。它是一個處理物件依賴項的過程,也就是將他們一起工作的其他的物件,只有通過構造引數、工廠方法引數或者(屬性注入)通過構造引數例項化或通過工廠方法返回物件後再設定屬性。當建立bean後,IoC容器再將這些依賴項注入進去。這個

Spring原始碼分析(二)(IoC容器的實現)(1)

    Ioc(Inversion of Control)——“控制反轉”,不是什麼技術,而是一種設計思想。在Java開發中,Ioc意味著將你設計好的物件交給容器控制,而不是傳統的在你的物件內部直接控制。理解好Ioc的關鍵是要明確“誰控制誰,控制什麼,為何是反轉(有

spring原始碼分析】IOC容器初始化(二)

前言:在【spring原始碼分析】IOC容器初始化(一)中已經分析了匯入bean階段,本篇接著分析bean解析階段。 1.解析bean程式呼叫鏈 同樣,先給出解析bean的程式呼叫鏈: 根據程式呼叫鏈,整理出在解析bean過程中主要涉及的類和相關方法。 2.解析bean原始碼分

jQuery2.0.3原始碼分析系列(28) 元素大小

章節導航 最近的分析都是有點不溫不火,基本都是基礎的回顧了 今年部落格的目標目前總的來說有2大塊 JS版的設計模式,會用jQuery來詮釋 JS版的資料結構,最近也一直在狠狠的學習中. HTML息息相關的的樣式 偏移量 offsetWidth off

jQuery2.0.3原始碼分析系列之(29) 視窗尺寸

.width() 基礎回顧 一般的,在獲取瀏覽器視窗的大小和位置時,有以下幾個屬性可以使用: 在不同的瀏覽器中,以下12個屬性所代表的意義也是不一樣的 特別需要注意的是,當使用或者不使用<!DOCTYPE>宣告顯示一個文件的時候,以上12個屬性的意義也會發生變化。 特在IE 9中

Spring原始碼分析——BeanFactory體系之介面詳細分析

Spring原始碼分析——BeanFactory體系之介面詳細分析   Spring的BeanFactory的繼承體系堪稱經典。這是眾所周知的!作為Java程式設計師,不能錯過!   前面的博文分析了Spring的Resource資源類Resouce。今天開始分析Spring的

Spring5原始碼分析系列(九)Spring事務原理詳解

終於等到了B站的薪資溝通電話,美滋滋,本節開始進入Spring資料訪問篇,講解spring事務,文章參考自Tom老師視訊。 事務基本概念 事務(Transaction)是訪問並可能更新資料庫中各種資料項的一個程式執行單元(unit)。 特點: 事務是恢復和併發控制的基

Spring原始碼分析BeanFactory (二)

前言 在前面我們簡單的分析了BeanFactory的結構,ListableBeanFactory,HierarchicalBeanFactory,AutowireCapableBeanFactory。主要核心類DefaultListableBeanFactor

Spring原始碼分析——IOC容器

1、IOC容器的概念 理解IOC容器的概念之前首先需要了解依賴翻轉(又稱依賴倒置)的概念 許多複雜的應用都是通過多個類之間的彼此合作實現業務邏輯的,這使得每個物件都需要管理自己與其合作物件的依賴,而如果這個過程如果交給物件自身實現將會導致程式碼的耦合度過高。因此

Spring-Cloud-Gateway原始碼分析系列| Spring-Cloud-Gateway初始化

推薦 Spring Boot/Cloud 視訊: Spring-Cloud專案使用EnableAutoConfiguration註解自動 初始化配置資訊,Spring-Cloud-Gateway同樣,Spring-Cloud-Gateway下的spring.f

Spring-Cloud-Gateway原始碼分析系列 | Spring-Cloud-Gateway之GatewayProperties初始化載入

推薦 Spring Boot/Cloud 視訊: 在Spring-Cloud-Gateway初始化時我們在GatewayAutoConfiguration配置中看到了有初始化載入GatewayProperties例項的配置,接下來學習下GatewayPrope

Spring原始碼分析(三)(IoC容器的依賴注入)(2)

protected void populateBean(String beanName, RootBeanDefinition mbd, BeanWrapper bw) { //這裡取得在BeanDefinition中設定的property值,這些property來自對BeanDefini