Struts2初始化流程及源碼分析

1.1 Struts2初始化

在講Struts2的初始化之前,應該為大家描述下Web應用中的過濾器Filter,這關系到我們對核心過濾器FilterDispatcher的正確理解。

Filter:一個filter是一個對象,為每個請求資源(一個servlet或靜態內容) ,或響應一個資源,或兩者,用于執行過濾任務。過濾器執行過濾是在doFilter方法中。每個過濾器方法訪問一個FilterConfig對象從中獲取初始化參數,filterConfig.getServletContext()可以獲得ServletContext對象使用。過濾器的配置在Web應用程序的web.xml中。

init():初始化過濾器,它的輸入參數javax.servlet.FilterConfig的一個實例,可以在這里初始化過濾要使用到的FilterConfig。該方法由Web容器自動調用。

doFilter():進行具體的過濾操作,這個方法以javax.servlet.ServletRequest請求信息, javax.servlet.ServletResponse響應信息,javax.servlet.FilterChain過濾鏈。過濾鏈,在Web應用程序中所有的過濾器會構成一個鏈狀,符合過濾條件的程序將會根據定義的順序執行所有鏈中的過濾器。在這個方法中調用FilterChain的 doFilter(javax.servlet.ServletRequest, javax.servlet.SerletResponse)方法就可以傳遞到鏈中的下一個過濾器。

destory():銷毀過濾器,可以在這里釋放使用完的資源,例如設置過濾器中FilterConfig為null。

綜上所述,在Web應用啟動時,會默認初始化Filter,調用Filter的init(FilterConfig filterConfig)方法,當請求到來時,會按順序執行web.xml中所配置Filter的doFilter(ServletRequest req, ServletResponse res, FilterChain chain)方法。

Struts2的核心過濾器FilterDispatcher實現的就是StrutsStatics, Filter接口,所以它本質就是一個過濾器,如下圖所示:

image

所以Struts2的初始化工作在Web應用啟動時,就可以通過FilterDispatcher核心過濾器init(FilterConfig filterConfig)方法來完成了。如下圖所示:

clip_image004

FilterDispatcher.init(FilterConfig filterConfig)方法中主要工作分為:

a) 創建Dispatcher類對象,將FilterDispatcher配置的初始化參數傳到該對象中;

b) 加載并解析配置文件,配置文件分為屬性配置文件、Bean配置文件兩種。Struts2的配置文件包括系統默認的配置文件: default.properties、struts-default.xml,以及插件配置文件、應用配置文件:struts-plugin.xml、struts.xml、struts.properties、web.xml。那么這六種配置文件的加載順序,如下:

1. default.properties

2. struts-default.xml

3. struts-plugin.xml

4. struts.xml

5. struts.properties

6. web.xml

加載順序如下圖所示:

clip_image006

c) 加載靜態資源配置參數: packages,該參數用來配置自動搜尋目錄;

小提示:

FilterDispatcher 實現的StrutsStatics接口,沒有定義業務方法,只定義了若干個常量。Struts2對常用的接口進行了重新封裝,比如HttpServletRequest、HttpServletResponse、HttpServletContext等。如下圖所示:

clip_image008

1.2 Struts2初始化源碼分析

1. Struts2 Web應用啟動時,根據web.xml配置的核心過濾器FilterDispatcher,會初始化FilterDispatcher:

clip_image010

2. 正如我們知道的,過濾器初始化時,會自動調用init()方法進行初始化工作,所以在FilterDispatcher啟動時,會自動調用init(FilterConfig filterConfig)方法,進行Struts2的初始化,首先在該方法中會創建org.apache.struts2.Dispatcher對象,將FilterDispatcher配置的初始化參數傳到該對象中,然后調用dispatcher.init()方法加載并解析配置文件,最后加載靜態資源配置參數packages。org.apache.struts2.dispatcher.FilterDispatcher.java源碼如下圖所示:

clip_image011

3. 在FilterDispatcher.init()方法中,首先創建Dispatcher類對象,并將FilterDispatcher配置的初始化參數傳到對象中;相關代碼,如下圖所示:

clip_image013

4. 然后通過dispatcher.init()方法,加載并解析Struts2配置文件,配置文件的加載與解析是由Provider類來實現完成的,所以可分為兩步:加載配置Provider、解析配置Provider,具體處理步驟如下:

a) 創建com.opensymphony.xwork2.config.ConfigurationManager,其中屬性List<ContainerProvider> containerProviders存放所有配置Provider。

b) init_DefaultProperties():初始化一個用來加載default.properties的DefaultPropertiesProvider,并存入至containerProviders。

c) init_TraditionalXmlConfigurations():默認根據struts-default.xml,struts-plugin.xml,struts.xml (可根據init-param:config 修改加載路徑) 分別創建三個 org.apache.struts2.config. StrutsXmlConfigurationProvider,并存入至containerProviders。

d) init_LegacyStrutsProperties():初始化初始化一個用來加載struts.properties的LegacyPropertiesConfigurationProvider,并存入至containerProviders。

e) init_CustomConfigurationProviders():根據init-param:configProviders初始化一個用戶自定義實現的ConfigurationProvider接口的Provider,并存入至containerProviders。

f) init_FilterInitParameters():初始化一個用來加載web.xml中initParams配置的ConfigurationProvider, 并存入至containerProviders。

g) init_AliasStandardObjects() :初始化一個用來為所配置的Bean與具體類映射的BeanSelectionProvider,并存入至containerProviders。

h) init_PreloadConfiguration():以上幾步存入ConfigurationProvider對象完畢后,按順序循環調用上面幾步存入的ConfigurationProvider的register、loadPackages、addPackage方法(先加載先解析),進行解析配置Provider。

小提示:

1. 加載配置Provider,其實就是加載配置文件;

2. 解析配置Provider,其實就是解析配置文件;

下面列出以上a-h步的相關代碼,如下圖所示:

1. Struts2中dispatcher.init()代碼:

clip_image015

2. Struts2中init_PreloadConfiguration()方法代碼:

clip_image017

3. XWork中configurationManager.getConfiguration()方法代碼:

clip_image019

4. XWork中configuration.reloadContainer()方法代碼:

clip_image021

5. Xwork中XmlConfigurationProvider.loadPackages()方法代碼:

clip_image023

6. Xwork中XmlConfigurationProvider.addPackage ()方法代碼:

clip_image025

4. 最后通過staticResourceLoader.setHostConfig(new FilterHostConfig(filterConfig))加載靜態資源配置參數:packages,值得注意的是,還有另外三個固定的包和該參數進行拼接,分別是org.apache.struts2.static、template、和org.apache.struts2.interceptor.debugging,中間用空格隔開,經過解析將包名變成路徑后存儲到一個名叫pathPrefixes的數組中,這些目錄中的文件會被自動搜尋;相關代碼,如下圖所示:

clip_image027

注:

關于源碼分析,大概分為兩種:流程源碼分析、過程源碼分析,因本人的初衷是流程源碼分析,所以以上的分析是根據初始化處理流程順序來進行分析的,并未對各個方法的過程細節做深入的講解,望見諒。

轉載于:https://www.cnblogs.com/mktao/archive/2012/08/30/2664296.html

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/379374.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/379374.shtml
英文地址,請注明出處:http://en.pswp.cn/news/379374.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

實驗1 數據庫操作

實驗1 數據庫操作一、實驗目的 1.掌握管理工具、T-SQL創建數據庫的方法。 2.掌握管理工具、T-SQL修改和查看數據庫的方法。 3.掌握管理工具、T-SQL刪除數據庫的方法。 4.掌握數據庫的附加與分離 二、實驗要求 1.創建實驗所用到的“網上購物系統”數據庫eshop。 三、實驗內容 1…

Java FileInputStream finalize()方法與示例

FileInputStream類的finalize()方法 (FileInputStream Class finalize() method) finalize() method is available in java.io package. finalize()方法在java.io包中可用。 finalize() method is used to assure that close() method of this FileInputStream invokes when th…

逆風飛揚,吳仁宏

摘自逆風飛揚,吳仁宏自傳 它是一個從"生而自卑"到"個性飛揚"的故事&#xff0c;當然具有傳奇色彩 中國人幾千年都不是天生的贏家&#xff0c;讓我們努力&#xff0c;為國為家為自己&#xff0c;做贏家&#xff01; 生存哲學 尼采 痛苦,挫折使生命遷長,使人…

ffmpeg 命令圖片和視頻相互轉換

1當前文件環境&#xff1a; ffmpeg -i test.mp4 -y -f image2 -ss 00:00:02 -vframes 1 -s 640x360 test.jpg ffmpeg -i test.mp4 -y -f image2 -ss 00:00:02 -vframes 1 -s 640x360 test.bmp 使用ffplay test.jpb ffplay test.bmp 都是可以打開的 參數介紹&#xff1a; -y 如…

如何點擊鏈接直接跳轉到app store指定應用下載頁面

轉載自&#xff1a;http://blog.csdn.net/zengconggen/article/details/6789420 NSString *str [NSString stringWithFormat:"http://itunes.apple.com/us/app/id%d", 436957167]; [[UIApplication sharedApplication] openURL:[NSURL urlWithString:str]];其中&…

COLLEGE.sql(復制的時候注意路徑!!!)

USE [master] GO /****** Object: Database [COLLEGE] Script Date: 2019/11/25 星期一 上午 08:57:11 / CREATE DATABASE [COLLEGE] ON PRIMARY ( NAME N’COLLEGE_m’, FILENAME N’F:\COLLEGE\COLLEGE.mdf’ , SIZE 51200KB , MAXSIZE UNLIMITED, FILEGROWTH 10240KB )…

【管理】「本能叛逆」與「理性叛逆」

叛逆是一般人認知的負面名詞&#xff0c;但是&#xff0c;很多人都忽略掉&#xff0c;它卻是人類進步的重要因子。觀察孩童的成長過程&#xff0c;十歲以后都會出現叛逆行為&#xff0c;相當令父母及師長頭痛。然而&#xff0c;叛逆卻是促使孩童突破家庭單一環境養成的認知與觀…

Java Double類parseDouble()方法的示例

Double類parseDouble()方法 (Double class parseDouble() method) parseDouble() method is available in java.lang package. parseDouble()方法在java.lang包中可用。 parseDouble() method is used to return the double value corresponding to the given String or in oth…

ffmpeg命令 拉流

1&#xff1a; 拉流播放:rtmp &#xff08;ffplay rtmp://server/live/streamName&#xff09; ffplay -x 480 -y 320 rtmp://58.200.131.2:1935/livetv/cctv1 2&#xff1a; 拉流存儲到文件:rtmp ffmpeg -i rtmp://58.200.131.2:1935/livetv/cctv1 -codec copy cctvrtmp.f…

小心pthread_cond_signal和SetEvent之間的差異

ZZ FROM: http://blog.csdn.net/absurd/article/details/1402433 轉載時請注明出處和作者聯系方式&#xff1a;http://blog.csdn.net/absurd 作者聯系方式&#xff1a;Li XianJing <xianjimli at hotmail dot com> 更新時間&#xff1a;2006-12-19 今天幫同事查一個多線…

eshop.sql(復制的時候注意路徑!!!)

USE [master] GO /****** Object: Database [eshop] Script Date: 2019/11/25 星期一 上午 08:54:14 / CREATE DATABASE [eshop] ON PRIMARY ( NAME N’eshop_dat’, FILENAME N’D:\eshop\eshop_dat.mdf’ , SIZE 10240KB , MAXSIZE 51200KB , FILEGROWTH 5120KB ) LOG O…

doublevalue_Java Double類doubleValue()方法與示例

doublevalueDouble類doubleValue()方法 (Double class doubleValue() method) doubleValue() method is available in java.lang package. doubleValue()方法在java.lang包中可用。 doubleValue() method is used to return the value denoted by this Double object converted…

ffmpeg 命令過濾器裁剪

1 圖片操作&#xff1a; 原圖&#xff1a; 使用ffplay 顯示左半邊 ffplay -i input.png -vf cropiw/2:ih:0:0 可以通過ffmpeg 保存 ffmpeg -i input.png -vf cropiw/2:ih:0:0 out.png 2 視頻操作&#xff1a; 原視頻&#xff1a; 顯示左半邊 ffplay -i cctvhttp.flv -vf …

去除aspx生成的頁面最開始的空行

使用.aspx生成的頁面一般都會有一個或多個空行&#xff0c;當然這些空行不會影響頁面在瀏覽器中的渲染結果&#xff0c;不過在查看源代碼的時候感覺有些別扭&#xff0c;我曾試著去刪除這些空行&#xff0c;但沒有成功&#xff0c;你知道你們有沒有去嘗試。 1 <% Page Langu…

PUBLISH.sql(復制的時候注意路徑!!!)

USE [master] – GO – /****** Object: Database [PUBLISH] Script Date: 2019/11/25 星期一 上午 09:00:04 / – CREATE DATABASE [PUBLISH] ON PRIMARY – ( NAME N’PUBLISH’, FILENAME N’F:\PUBLISH\PUBLISH.mdf’ , SIZE 51200KB , MAXSIZE UNLIMITED, FILEGROWTH …

c ++ 函數的esp指針_在C ++中通過指針訪問成員函數

c 函數的esp指針Create a class along with data member and member functions and then access the member functions by using a pointer in C. 創建一個類以及數據成員和成員函數&#xff0c;然后使用C 中的指針訪問成員函數。 如何通過指針訪問成員函數&#xff1f; (How…

[iphone-cocos2d]分享一段Objective-C可調用的游戲中播放音樂(1)

首先需要引入AudioTool 這個framework 代碼 -(id)initWithPath:(NSString *)path{ UInt32 size, maxPacketSize; char*cookie; inti; if(gThereIsAnActiveTrack) { NSLog("*** WARNING *** GBMusicTrack only plays one track at a time…

匯編語言-010(循環移位ROL,ROR 、進位循環進位RCL,RCR 、有符號數溢出 、雙精度移位SHLD,SHRD、SHL和ADD計算 、位運算應用)

1 &#xff1a;循環移位ROL,ROR,帶進位循環進位RCL,RCR .386 .model flat,stdcall.stack 4096 ExitProcess PROTO,dwExitCode:DWORD.code main PROC;循環左移mov al,40h ;AL 010000000brol al,1 ;AL 100000000b ,CF 0rol al,1 ;AL 000000001b ,CF 1rol al,1 ;A…

[Z]POJ 計算幾何入門題目推薦[轉PKKJ]

http://www.cnblogs.com/eric-blog/archive/2011/05/31/2064785.html http://hi.baidu.com/novosbirsk/blog/item/723a9727a9ab8804918f9dca.html其實也談不上推薦&#xff0c;只是自己做過的題目而已&#xff0c;甚至有的題目尚未AC&#xff0c;讓在掙扎中。之所以推薦計算幾何…

2013年 833c語言程序 江南大學 (A卷)

1.編寫程序實現求兩個整數最大公約數和最小公倍數. 方法一&#xff1a;輾轉相除法 算法思路&#xff1a;兩個整數a,b,其中a>b&#xff0c;求其最大公約數和最小公倍數 步驟① a%bc,其中c為余數 步驟② 若余數c為0&#xff0c;即a可以把b給整除,也就是說這里的b就是其最大公…