在前面我們已經完成了ioc,di,aop的實現,基本的功能都已經完成了,我們的手寫框架也能勉強使用起來。為了讓我們的框架能夠使用起來比較簡單,這一節我們來實現註解和xml的配置。
tips
本章的xml和註解的功能都是為實現bean的建立,其他如aop等功能可仿造實現。
如果有同學測試過我們寫好的框架,可能會感受到使用起來非常麻煩,在測試的時候我們需要顯示的來定義bean以及執行過程中需要的其他物件。
public void test() throws exception
複製**
如上為測試乙個aop的功能,需要定義很多的物件來完成功能,這還只是乙個物件的功能增強,在實際使用中肯定會有大量的例項。這樣在使用起來就變得及其麻煩了。參考spring中,可以通過xml和annotation的方式來簡化類定義或者其他一些處理。
在實際實現之前,我們先來巨集觀的看一些註解和xml是如何來解析的。
基本上在spring中xml就是這樣工作的,同理,註解也差不多是這樣乙個過程。
上面的這一過程實際上就是我們需要實現的功能,現在我們就根據以上過程進行實現吧。
定義xml標記
這一小節的內容並不重要,實際就我們的開發中作用並不大,稍微了解即可。沒興趣的可以直接跳到下一節。
定義xml標記的方式有dtd和xsd兩種,假設我想定義乙個下面這樣的xml標記:
<?xml version="1.0"?>
tove
jani
reminder
don't forget me this weekend!
複製**
那麼我們既可以用dtd實現,也可以用xsd實現:
dtd
#pcdata)>
#pcdata)>
#pcdata)>
#pcdata)>
複製**
xsd
<?xml version="1.0"?>
""targetnamespace=""
xmlns=""
elementformdefault="qualified">
"note">
"to"
type="xs:string"/>
"from"
type="xs:string"/>
"heading"
type="xs:string"/>
"body"
type="xs:string"/>
複製**
這節內容只是稍微提下,有興趣的可以搜一些資料學習。
載入xml檔案
要來載入檔案那麼首先我們需要知道這個檔案的位置,很明顯這個位置需要由使用者來指定,由使用者來告訴我們需要載入那些配置檔案,那麼使用者該如何來指定呢?
這裡我們需要定義新的類和介面來完成這件事,這個新定義的類用來完成xml檔案的載入,解析以及對bean例項的建立和註冊等。同時該類是給使用者使用的,在bean建立後還需要讓使用者能夠取到容器中的例項,即該類還需要具備beanfactory的部分功能。
如何載入配置檔案
說到載入,首先我們需要明白這些配置檔案可能會以什麼樣的形式展現,一般來說有著以下的型別:
可能還有其他不同的形式,當然這不重要。我們需要明白的是很明顯不同形式的內容載入的方式肯定是不同的,比如通過檔案系統載入的是獲得乙個檔案,而url形式的是從網路獲取資料。所以我們需要為每一種方式都提供個性的載入方式。
載入的方式不一樣,那麼解析呢?
解析xml,我們都是需要獲取到xml的流資訊,都是解析xml的inputstream,所以雖然載入方式各不相同,但是解析的方法是可以通用的。
根據上面的分析,我們可以知道,載入的過程實際上就是獲取乙個inputstream的過程,很明顯每一種方式獲取配置檔案都需要最終返回乙個inputstream,這裡我們定義乙個獲取inputstream的介面。
對於配置檔案的載入實際上不管通過哪一種方式,實際上都是對檔案進行操作,為了方便能夠對解析提供一致的介面,我們需要對不同方式載入進行抽象,使其能接受任意型別的載入方式物件。這裡我們定義resource介面來表示xml資源,不同的實現類表示不同的載入方式。resource介面具備一部分檔案的特性。
到了現在我們還有乙個很重要的問題,就是我們如何來分辨當前需要載入的配置是屬於哪一種型別呢?只有解決了這一問題才能正確的解析。
這裡我們使用字首匹配的方式來分配不同型別的配置檔案載入器,比如:
通過不同的字首來來返回不同的物件,如果看過前面幾節的同學應該馬上就能反應過來這裡肯定要用工廠模式了[笑]。
那麼載入配置檔案這一行為在什麼時候進行呢?
如何解析配置檔案
載入已經完成了,就是說我們現在已經取到不同的resource,那麼現在如何對其進行解析呢?
對於xml型別的檔案解析我們這裡使用dom4j,這個東西沒必要深入研究,要用到的時候查下api就行了。對於xml的解析就是獲取節點,然後對獲取節點的內容。回顧我們之前在做ioc的時候,建立乙個bean首先是需要獲取beandefinition。xml這裡也一樣,根據解析到的內容構造beandefinition,通過beandefinitionregistery註冊。在對bean例項化時取用。所以很明顯我們需要定義乙個新的介面用於解析resource,將解析後的內容封裝為beandefinition並註冊。
好了,到這裡關於xml的載入和解析基本就完成了,而對於annotation的解析流程基本也是這樣的,使用者指定需要掃瞄的包,框架遍歷包所在目錄及子目錄,記錄下相應被註解修飾的類,反射生成class物件,獲取class物件資料生成beandefinition。類圖在上面也已經體現出來了。後面就需要我們去寫**了。
相關的**已經託管到github
Spring系列之手寫自定義的 Enable 註解
在我們日常開發普通的spring framework專案過程中 enable用的不是很多,但在springboot開發過程,我們經常會遇到 enable開始的好多註解,比如 enablewebmvc enableeurekaserver enableasync enablescheduling等,今...
手寫Spring事物註解
在spring中使用 transactional註解屬於聲名式事物,但我們要自己實現此類功能,就需要對程式設計試事物進行封裝。首先在資料庫新建了個user空表 在程式中新增兩條資料,在中間丟擲1 0的錯誤 執行後,檢視資料庫內容,已經插入了一條內容 加上自定義的事物註解 再次執行,檢視資料庫內容,已...
手寫系列之手寫高斯牛頓法 基於Eigen
重複造輪子雖然很多人不推薦,但是個人認為,不重複造一下輪子,也就不能真正的懂輪子的寫作邏輯優點和考慮,更別說優化輪子.會導致像高中一聽就會,一做就錯的感覺,所以筆者挑選一下極具代表性的演算法進行手寫,收貨頗豐.本 基於高翔博士 include include include opencv2 open...