搭建輕量級Java Web框架快速搭建開發框架如何載入配置文件如何實現一個簡單的 IOC 容器如何載入指定的類如何初始化框架 *註解開發 目標:打造一個輕量級的 MVC 框架,Controller 是MVC的核心,類似於 SpringMVC。通過 Controller 註解來定義 Controlle ...
搭建輕量級Java Web框架
快速搭建開發框架
如何載入配置文件
如何實現一個簡單的 IOC 容器
如何載入指定的類
如何初始化框架
*註解開發
目標:
打造一個輕量級的 MVC 框架,Controller 是MVC的核心,類似於 SpringMVC。
通過 Controller 註解來定義 Controller 類,在該類中,可以通過 Inject 註解定義一系列 Service 成員變數,這就是"依賴註入"。
此外有一系列的被 Action 註解所定義的方法(Action方法),在這些Action方法中,調用了 Service 成員變數的方法來完成具體的業務邏輯。
若返回 View 對象,則表示 JSP 頁面;若返回 Data 對象,則表示一個 JSON 數據。
簡單來說,就是一個 Controller 類包含多個 Action方法,可以返回 View 或 Data 對象,分別對應JSP頁面或 JSON 數據。
@Controller 註解
@Service 註解
@Action 註解
@Inject 註解
View類:視圖路徑,模型數據
Data類:模型數據
Param類:封裝有請求參數的對象
Request對象:封裝請求信(請求方法和請求路徑)
Handler對象:封裝 Action信息(控制器類和處理方法)
核心:DispatchServlet:調用init方法時,初始化 Helper 類。service 方法中進行請求的獲取與請求的處理
PropUtil→ConfigHelper:載入配置項,獲取配置項定義的內容
ClassUtil→ClassHelper:獲取指定包名下所有類,所有 Controller 類,所有 Service 類,所有 Bean 類。(CLASS_SET容器的概念)
ReflectionUtil→BeanHelper:創建了一個 Bean 容器,在 BeanMap中存放了 Bean類和 Bean實例的映射關係。(BEAN_MAP就是一個容器)
IocHelper:實現依賴註入
ControllerHelper:處理請求和請求處理方法之間的關係(ACTION_MAP也是一個容器)。
HelperLoader:四個Helper類通過一個入口程式來載入,實際上是載入他們的靜態塊。
基礎:
定義框架配置項:
jdbc相關配置、項目基礎包名、JSP基礎路徑、靜態資源文件的基礎路徑
提供相關配置項常量
載入配置項,獲取配置項定義的內容:由 PropUtil 提供支持(從當前線程來載入配置文件)→ ConfigHelper
開發類載入器:
開發一個類載入器來載入基礎包名下的所有類,比如使用了某註解的類,或實現了某介面的類,再或者繼承了某父類的所有子類。
ClassUtil工具類:提供與類操作的相關方法,
如
獲取類載入器:只需要獲取當前線程中的ClassLoader即可
載入類:public static Class<?> forName(String className, boolean initialize,ClassLoader loader)。其中 initialize 表示是否載入靜態代碼塊。
獲取指定包名下的所有類。
獲取應用包名下的所有類、應用包名下的所有 Service 類,應用包名下的所有 Controller 類。
獲取 帶有 Controller 和 Service 類(Bean類,歸 IOC 容器去管理)→ ClassHelper
實現 Bean 容器(由容器來創建對象←通過反射結合ClassHelper來實現)
ReflectionUtil(反射工具類):創建實例,調用方法,設置成員變數的值
BeanHelper:獲取框架管理的 Bean 類,隨後通過反射工具類來創建實例。將每次創建的對象都放入到一個靜態的 Map<Class<?>, Object>類中。
實現依賴註入功能(通過容器對標註有某註解的成員變數進行實例化):
用 Inject 註解來實現對 Service 實例化。
具體實現:先通過BeanHelper獲取所有的BeanMap結構,記錄了類與對象的映射關係。然後遍歷這個映射關係,分別取出 Bean 類與Bean實例,
進而通過反射獲取類中所有的成員變數。繼續遍歷這些成員變數,看這些成員變數是否帶有 Inject 註解,若帶有該註解,則從 BeanMap 中,則從
BeanMap中根據Bean類取出Bean實例。最後通過 ReflectionUtil#setField 方法來修改當前成員變數的值。
載入Controller:
通過 ClassHelper,我們可以獲取所有定義了Controller 註解的類,可以通過反射獲取該類中所有帶有Action註解的方法(簡稱“Action”)方法,
獲取 Action 註解中的請求表達式,進而獲取請求方法和請求路徑,封裝一個請求對象(Request),和處理對象(handler) ,最後將 Request和Handler
建立一個映射關係,放入一個 ActionMap中,並提供一個可根據請求方法與請求路徑獲取處理對象的方法。
ControllerHelper:封裝一個 ActionMap,通過它存放Request和Handler之間的映射,然後通過 ClassHelper 來獲取所有帶有Controller註解的類,
接著遍歷這些 Controller 類,從 Action 註解中提取 URL,最後初始化 Request 和 Handler之間的映射。
核心:
請求轉發器(處理請求和響應):
處理所有請求,從HttpServletRequest對象中獲取請求方法和請求路徑。通過 ControllerHelper#getHandler方法來獲取Handler對象。
拿到 Handler 對象後,我們可以方便地獲取 Controller 的類,金額通過 BeanHelper.getBean 方法獲取 Controller 的實例對象。
隨後可以從 HttpServletRequest 對象中獲取所有請求參數,並將其初始化到一個 Param 的對象中。
還可以從 Handler 對象中獲取 Action 的方法返回值,該返回值可能有兩種情況:
(1)若返回值是 View 類型的視圖對象,則返回一個 JSP 頁面。
(2)若返回值是 Data 類型的數據對象,則返回一個 JSON 數據。
總結:
通過 Controller 註解定義了 Controller類,通過Inject 註解來實現依賴註入,通過Action註解來定義Action方法。
通過一系列的 Helper 類來初始化 MVC 框架。通過 DispatchServlet 來處理所有的請求,根據請求方法和請求路徑來調動具體的 Action 方法,判斷
Action 方法的返回值,若為 View類型,則條狀到 JSP 頁面,若為 Data類型,則返回 JSON 數據。