摘要:讀取定義的內(nèi)容,將用戶定義的表示成,是在容器中對的抽象,記錄了配置的信息。的生命周期在初始化后,并沒有被實際的創(chuàng)建。工作過程當目標對象被調(diào)用時,會觸發(fā)的回調(diào)函數(shù)進行攔截。
IoC容器的實現(xiàn)
控制反轉(zhuǎn)(Inversion of Control,縮寫為IoC),是面向?qū)ο缶幊讨械囊环N設(shè)計原則,可以用來減低計算機代碼之間的耦合度。
依賴反轉(zhuǎn)是什么依賴反轉(zhuǎn)在Spring中的體現(xiàn)是依賴注入。
類通過引用來進行合作,這種引用形成了類之間的依賴,如果這種依賴關(guān)系需要對象自己管理,那么代碼會產(chǎn)生高度的耦合,導(dǎo)致開發(fā)和測試上的困難。如果這種依賴的管理交給框架來做,將簡化面向?qū)ο笙到y(tǒng)的復(fù)雜性,這就是依賴的反轉(zhuǎn)。
Spring中的容器是什么容器用來管理應(yīng)用中的對象和其之間的依賴關(guān)系。BeanFactory是對容器的一種抽象,ApplicationContext是其高級實現(xiàn)。
IoC的初始化過程整體過程分三步:
Resourece定位,也就是定位定義Bean資源的位置。Resourece的位置是多樣的,使用比較多的是FileSystemResourece。
BeanDefinition載入。讀取定義的內(nèi)容,將用戶定義的Bean表示成BeanDefinition,BeanDefinition是在容器中對POJO的抽象,記錄了配置的bean信息。
向IoC容器注冊BeanDefinition,IoC用HashMap結(jié)構(gòu)來維護注冊的BeanDefinition。
注意這里只是有Bean的載入,而不是依賴注入,依賴注入發(fā)生在第一次通過getBean向容器獲取Bean的時候。
依賴注入過程在發(fā)起getBean方法時,才會進行依賴注入,創(chuàng)建響應(yīng)的bean。
依賴注入過程如下:
判斷單例bean是否已經(jīng)創(chuàng)建,創(chuàng)建過的無需重復(fù)創(chuàng)建。
遞歸創(chuàng)建依賴的bean。
最后創(chuàng)建目標bean實例。
實例化Java對象。采用了CGLIB或者JVM反射機制來生成對象。CGLIB可以在運行期動態(tài)的生成新的class。
注入屬性依賴。
Bean的生命周期在IoC初始化后,Bean并沒有被實際的創(chuàng)建。在getBean后,才會有bean的實例化,bean的生命周期如下:
創(chuàng)建bean實例->設(shè)置bean的屬性->調(diào)用bean的初始化方法(initialization)->應(yīng)用可以使用bean->容器關(guān)閉,銷毀bean
Bean的lazy init上述可知,bean會在使用時才會真正的創(chuàng)建,這防止了創(chuàng)建大量用不到的bean實例。
當然,可以通過設(shè)置參數(shù),讓bean在IoC容器初始化完畢后就創(chuàng)建。
IoC感知的BeanBean一般情況下不需要知道IoC容器的存在,有時候則需要。Bean可以實現(xiàn)一些aware接口來獲得想要的容器屬性。
如ApplicationContextAware,可以在Bean中獲得上下文,從而在Bean中使用上下文。
AOP的實現(xiàn) AOP的作用分離關(guān)注點使解決特定領(lǐng)域問題的代碼從業(yè)務(wù)邏輯中獨立出來。
基本概念Advice通知:描述方法調(diào)用注入的切面行為。
Pointcut切點:用來描述需要增強的方法集合。
Advisor通知器:將Advice和Pointcut結(jié)合起來。
在代理模式中,會設(shè)計一個和目標對象有著一致接口的代理對象Proxy,客戶端對目標對象的請求都會發(fā)送給代理對象,而客戶端對此毫無察覺。
該模式使得Proxy有機會對原始的對象的行為進行一定的修改,可以在執(zhí)行前和執(zhí)行后分別執(zhí)行一定的動作,從而增強原始行為。
AopProxy的實現(xiàn)原理首先需要定義一些Advisor,這些Advisor定義了需要織入的增強功能,也就是涵蓋了通知的內(nèi)容。然后定義ProxyFactoryBean,它將會生成目標的代理對象。在配置中,ProxyFactoryBean需要知道其代理的目標是誰,代理的接口是哪個,有哪些Advisor需要添加。
ProxyFactoryBean生成AopProxy過程:
初始化通知器鏈。通過getBean獲取通知器的bean,然后加入。ProxyFactoryBean只在第一次獲得AopProxy時初始化。
生成代理對象。
JDK生成,需要設(shè)置ClassLoader和代理接口。
CGLIB生成。
AopProxy工作過程:
當目標對象被調(diào)用時,會觸發(fā)Proxy的回調(diào)函數(shù)進行攔截。
首先獲取攔截器。從上述中初始化的通知器鏈中,遍歷并獲取匹配目標方法的通知器,然后獲取通知器對應(yīng)的攔截器,該結(jié)果會被緩存。
調(diào)用器會依次迭代調(diào)用攔截器(interceptor)進行增強,最后調(diào)用目標方法。
通知器封裝為攔截器:
攔截器默認分為三類:MethodBeforeAdviceIntercepter、AfterReturn...、Throws...。
一個Advice會可能是MethodBeforeAdvice、AfterReturn...、Throws...其中的一個或者多個。
根據(jù)Advice的種類,適配器AdviceAdapter將其包裝為相應(yīng)的intercepter,intercepter中的invoke方法會根據(jù)before、after或者throw將advice的增強行為放置到適當位置。適配器默認是上述的三種,可以自定義adapter注冊進來,以生成自己定制的intercepter。
調(diào)用器執(zhí)行攔截器鏈的時候,遞歸過程:process(調(diào)用器)->invoke(intercepter)->process(調(diào)用器)->invoke(下一個intercepter)...->目標方法。所以intercepter會根據(jù)自己的種類在遞歸調(diào)用前或者后執(zhí)行advice的方法。
文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請注明本文地址:http://systransis.cn/yun/70796.html
摘要:與容器與容器的關(guān)系為容器提供了宿主環(huán)境。容器通過初始化建立,是注冊在容器中的監(jiān)聽器,當容器初始化時,監(jiān)聽器會收到該事件從而發(fā)起容器的初始化。是處理請求的轉(zhuǎn)發(fā)器,從而響應(yīng)的請求。接著將數(shù)據(jù)進行合并,然后將數(shù)據(jù)放入中進行暴露。 Spring MVC 與 Web IoC容器與Web容器的關(guān)系 ServletContext為IoC容器提供了宿主環(huán)境。IoC容器通過ContexLoaderLis...
摘要:構(gòu)造函數(shù)注入通過調(diào)用類的構(gòu)造函數(shù),將接口實現(xiàn)類通過構(gòu)造函數(shù)變量傳入。而在中,其使用橫切技術(shù),將這類代碼從原屬的封裝對象中提取出來,封裝到一個可重用模塊中,稱為。 最近實習用到Spring的開發(fā)框架,但是之前沒有接觸過,因此希望利用網(wǎng)上的資源來學習以下。 Spring官方給出了非常全面的介紹,非常適合我這種完全的小白……在這一系列學習中,我閱讀的主要資源是5.1.2 Reference ...
摘要:我自己總結(jié)的學習的系統(tǒng)知識點以及面試問題,已經(jīng)開源,目前已經(jīng)。目前最新的版本中模塊的組件已經(jīng)被廢棄掉,同時增加了用于異步響應(yīng)式處理的組件。每一次請求都會產(chǎn)生一個新的,該僅在當前內(nèi)有效。顯而易見,這種模式存在很多問題。 我自己總結(jié)的Java學習的系統(tǒng)知識點以及面試問題,已經(jīng)開源,目前已經(jīng) 41k+ Star。會一直完善下去,歡迎建議和指導(dǎo),同時也歡迎Star: https://githu...
摘要:會一直完善下去,歡迎建議和指導(dǎo),同時也歡迎中用到了那些設(shè)計模式中用到了那些設(shè)計模式這兩個問題,在面試中比較常見。工廠設(shè)計模式使用工廠模式可以通過或創(chuàng)建對象。 我自己總結(jié)的Java學習的系統(tǒng)知識點以及面試問題,已經(jīng)開源,目前已經(jīng) 41k+ Star。會一直完善下去,歡迎建議和指導(dǎo),同時也歡迎Star: https://github.com/Snailclimb... JDK 中用到了那...
摘要:開頭正式開啟我入職的里程,現(xiàn)在已是工作了一個星期了,這個星期算是我入職的過渡期,算是知道了學校生活和工作的差距了,總之,盡快習慣這種生活吧。當時是看的廖雪峰的博客自己也用做爬蟲寫過幾篇博客,不過有些是在前人的基礎(chǔ)上寫的。 showImg(https://segmentfault.com/img/remote/1460000010867984); 開頭 2017.08.21 正式開啟我...
閱讀 2165·2021-11-12 10:36
閱讀 2157·2021-09-03 10:41
閱讀 2779·2021-08-19 10:57
閱讀 1246·2021-08-17 10:14
閱讀 1498·2019-08-30 15:53
閱讀 1219·2019-08-30 15:43
閱讀 983·2019-08-30 13:16
閱讀 2995·2019-08-29 16:56