SpringMVC流程全解析(2)

接著分析DispatchServlet,按照慣例蟆融,依舊貼出一張清晰醒腦的大圖绰播,這張圖清晰的描繪了關于DispatchServlet的類繼承關系仗颈,如下:


DispatchServlet.png

還是先從web.xml的配置說起,從上面的關系圖中我們可以看出DispatchServlet實際也是一個實現(xiàn)了Servlet標準接口的類诸尽,所以要想web應用正常跑原杂,我們必須在web.xml中注冊這個Servlet,如圖:


web.png

在開始分析DispatchServlet之前您机,我想跟大家細細的講講Servlet穿肄。Servlet主要是用來處理客戶端請求并封裝響應結果通過其內部的service方法發(fā)送給客戶端,如圖中所示:
servlet.png

其實從這張圖就可以看出际看,Sevlet是有一個生命周期的咸产,并且它從創(chuàng)建到銷毀都是在一個Servlet容器中進行的。在SpringMVC中Servlet的框架是由兩個java包組成的:javax.servlet和javax.servlet.http仲闽;javax.servlet中定義了一套標準化的servlet類都必須實現(xiàn)或者擴展的通用接口和類脑溢。javax.servlet.http中定義了基于Http通訊的實現(xiàn),當Web容器接收到servlet請求時赖欣,不管是get屑彻,put還是別的,它會把請求封裝成一個個的HttpServletRequest對象顶吮,然后傳給Servlet#service方法進行處理社牲,最后返回一個HttpServletResponse對象返回。關于Servlet容器的銷毀悴了,其實servlet容器會先調用servlet#destroy方法搏恤,先銷毀servlet對象以及與其關聯(lián)的ServletConfig對象汗菜,最后再實現(xiàn)容器的關閉。

擴展點:從一開始的那種類繼承關系圖中我們可以看出挑社,如果我們想定義我們自己的Servlet對象陨界,我們完全可以學著SpringMVC的方式繼承HttpServlet,但切記寫完之后要在web.xml中注冊痛阻。

1.關于DispatchServlet的初始化

按照套路菌瘪,我們得先看HttpServlet的Init方法,因為這個Init方法是Servlet容器記載Servlet類的數據到內存中的開始阱当,它首先會創(chuàng)建一個ServletConfig對象俏扩,然后在創(chuàng)建一個Servlet對象,最后調用這個Init方法將Servlet對象與ServletConfig關聯(lián)起來進行初始化的操作弊添,而在SpringMVC中這個方法的實現(xiàn)在HttpServletBean中录淡,如圖:


HttpServletBean.png

看下其HttpServletBean#Init方法的邏輯:


HttpServletBean#Init.png

實現(xiàn)流程如下:
1.獲取在web.xml中配置servletConfig參數(也就是在init-param配置項中的參數)的并且進行封裝及驗證,通過校驗missingProps來驗證某些參數的必要性油坝,如果有些missingProps項沒有初始化的話嫉戚,將拋出異常(內部細節(jié)讀者可自行查閱);

2.將當前這個servlet轉為BeanWrapper澈圈,使Spring對其能進行一些屬性的填充彬檀;
3.通過ResourceLoader對配置資源進行解析(也就是我們在web.xml中配置的springmvc的配置文件);
4.InitServletbean方法留給子類擴展的瞬女,其主要在FrameworkServlet進行實現(xiàn)窍帝,也就是為了對servletBean進行初始化;


InitServletbeanMethod.png

InitServletbean.png

InitServletbean主要干了兩件事诽偷,初始化WebApplicationContext以及FrameworkServlet坤学。

2.WebApplicationContext的初始化

來看initWebApplicationContext,貼上代碼报慕,一步一步分析:

initWebApplicationContext.png

流程如下:
1.先去根據servletContext對象獲取最上層的WebApplicationContext深浮,這個地方不懂的請看之前寫過的SpringMVC流程全解析(1);
2.判斷當前WebApplicationContext是否被創(chuàng)建過,如果是卖子,那么將其設置到rootContext略号,并且對已經創(chuàng)建的WebApplicationContext進行配置及刷新(這一步咋們在后面細說);
config&refresh.png

3.如果沒有被創(chuàng)建過刑峡,那么通過servlet的contextAttribute查找ServletContext中對于的屬性洋闽,默認是WebApplicationContext.class.getName()+".ROOT",也就是ContextLoaderListener加載時創(chuàng)建的XmlWebApplicationContext實例來進行查找突梦。

擴展:這個地方我們其實可以重寫這個初始化的邏輯來創(chuàng)建我們自己的WebApplicationContext诫舅,但是必須要在web.xml中創(chuàng)建初始化contextAttribue的key值,SpringMVC中默認是WebApplicationContext.class.getName()+".ROOT"宫患;

如果上面還是沒法獲取到刊懈,那就只能根據ContextLoaderListener創(chuàng)建的rootContext進行創(chuàng)建了。通過servlet的初始化參數contextClass,如果沒有配置的話就是XmlWebApplicationContext.class虚汛,然后通過反射實例化WebApplicationContext匾浪,然后將其與ContextLoaderListener創(chuàng)建的XmlWebApplicationContext關聯(lián),同時獲取contextConfigLocation屬性卷哩,并配置在servlet初始化參數中蛋辈。最后根據創(chuàng)建的XmlWebApplicationContext初始化Spring環(huán)境,加載配置文件将谊。
4.使用AbstractApplicationContext的refresh方法進行配置文件的加載冷溶,這是個模板方法,實現(xiàn)邏輯在DispatchServlet中尊浓,主要是根據WebApplicationContext刷新spring在web功能中所必須使用的全局變量逞频。

initStrategies.png
initStrategies.png

到了這一塊,我們得結合著我們得SpringMVC配置文件進行講解了栋齿,我得讓你清晰的知道為啥SpringMVC配置文件就得這么配置苗胀。

1.initMultipartResolver,initLocaleResolver瓦堵,initThemeResolver

這是SpringMVC用來處理文件上傳的柒巫,當然,要使用它谷丸,并不是以下這一處配置堡掏,你還必須在Web應用的上下文中添加對應的MultipartResolver,也是是在controller的方法開頭添加刨疼,這樣springMVC才會對它進行處理泉唁。代碼如下:


multipartResolver.png

我們的配置文件內容:


Paste_Image.png

簡單解釋下,CommonsMultipartResolver是SpringMVC默認的文件解析器揩慕,如果要想自定義亭畜,繼承這個類做些實現(xiàn)即可,關于property屬性迎卤,這些都在CommonsFileUploadSupport定義好的拴鸵,CommonsMultipartResolver繼承了CommonsFileUploadSupport這個類。
關于initLocaleResolver蜗搔,initThemeResolver與initMultipartResolver實現(xiàn)方式基本大同小異劲藐,SpringMVC都有默認的實現(xiàn)類,查看DispatchServlet.properties可以看到樟凄。
Paste_Image.png

2.HandlerMapping

當客戶端發(fā)出請求時聘芜,DispatchServlet會將請求提交給HandlerMapping,然后HandlerMapping根據WebApplicationContext的配置來回傳給DispatchServlet相應的Controller缝龄,按照慣例汰现,依舊按照代碼講述挂谍。

Paste_Image.png

1.默認情況下,它會去加載當前系統(tǒng)中所有實現(xiàn)了HandlerMapping接口的bean瞎饲,如圖所示:


handlerMapping.png

2.但是我們可以在web.xml文件中配置detectAllHandlerMappings為false口叙,那樣就會只加載我們在Springmvc配置文件中加載的HandlerMapping了。

detectAllHandlerMappings.png
RequestMappingHandlerMapping.png

此時嗅战,SpringMVC將會查找為handlerMapping的bean庐扫,作為當前系統(tǒng)唯一的handlerMapping。

Paste_Image.png

如果沒有定義的話仗哨,那么就會去找在DispatchServlet.properties文件中定義的HandlerMapping了形庭,SpringMVC默認是以BeanNameUrlHandlerMapping作為映射策略的實現(xiàn)。


Paste_Image.png

擴展點:這個地方其實可以通過重寫DispatchServlet#getDefaultStrategies自定義HandlerMapping策略厌漂。

好了萨醒,今天就講到這里,最后總結下苇倡,其實springMVC流程看起來還是很清晰富纸,但是我們要學會透過這個流程去看內部的實現(xiàn),去看SpringMVC中一些好的設計點旨椒,好的實現(xiàn)方式晓褪。這些我決定在寫完這個系列文章的最后給大家再總結。

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯(lián)系作者
  • 序言:七十年代末综慎,一起剝皮案震驚了整個濱河市涣仿,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌示惊,老刑警劉巖好港,帶你破解...
    沈念sama閱讀 222,183評論 6 516
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異米罚,居然都是意外死亡钧汹,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,850評論 3 399
  • 文/潘曉璐 我一進店門录择,熙熙樓的掌柜王于貴愁眉苦臉地迎上來拔莱,“玉大人,你說我怎么就攤上這事隘竭√燎兀” “怎么了?”我有些...
    開封第一講書人閱讀 168,766評論 0 361
  • 文/不壞的土叔 我叫張陵,是天一觀的道長。 經常有香客問我桑逝,道長击费,這世上最難降的妖魔是什么赋兵? 我笑而不...
    開封第一講書人閱讀 59,854評論 1 299
  • 正文 為了忘掉前任,我火速辦了婚禮搔预,結果婚禮上霹期,老公的妹妹穿的比我還像新娘。我一直安慰自己拯田,他們只是感情好历造,可當我...
    茶點故事閱讀 68,871評論 6 398
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著船庇,像睡著了一般吭产。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上鸭轮,一...
    開封第一講書人閱讀 52,457評論 1 311
  • 那天臣淤,我揣著相機與錄音,去河邊找鬼窃爷。 笑死邑蒋,一個胖子當著我的面吹牛,可吹牛的內容都是我干的按厘。 我是一名探鬼主播医吊,決...
    沈念sama閱讀 40,999評論 3 422
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼逮京!你這毒婦竟也來了卿堂?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 39,914評論 0 277
  • 序言:老撾萬榮一對情侶失蹤懒棉,失蹤者是張志新(化名)和其女友劉穎御吞,沒想到半個月后,有當地人在樹林里發(fā)現(xiàn)了一具尸體漓藕,經...
    沈念sama閱讀 46,465評論 1 319
  • 正文 獨居荒郊野嶺守林人離奇死亡陶珠,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 38,543評論 3 342
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了享钞。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片揍诽。...
    茶點故事閱讀 40,675評論 1 353
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖栗竖,靈堂內的尸體忽然破棺而出暑脆,到底是詐尸還是另有隱情,我是刑警寧澤狐肢,帶...
    沈念sama閱讀 36,354評論 5 351
  • 正文 年R本政府宣布添吗,位于F島的核電站,受9級特大地震影響份名,放射性物質發(fā)生泄漏碟联。R本人自食惡果不足惜妓美,卻給世界環(huán)境...
    茶點故事閱讀 42,029評論 3 335
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望鲤孵。 院中可真熱鬧壶栋,春花似錦、人聲如沸普监。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,514評論 0 25
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽凯正。三九已至毙玻,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間廊散,已是汗流浹背淆珊。 一陣腳步聲響...
    開封第一講書人閱讀 33,616評論 1 274
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留奸汇,地道東北人施符。 一個月前我還...
    沈念sama閱讀 49,091評論 3 378
  • 正文 我出身青樓,卻偏偏與公主長得像擂找,于是被迫代替她去往敵國和親戳吝。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 45,685評論 2 360

推薦閱讀更多精彩內容