SpringMVC(四)處理模型數據

一、Spring?MVC?提供了以下幾種途徑輸出模型數據:

ModelAndView: 處理方法返回值類型為ModelAndView時, 方法體即可通過該對象添加模型數據

Map?Model: 入參為org.springframework.ui.Model、org.springframework.ui.ModelMap 或java.uti.Map 時,處理方法返回時,Map中的數據會自動添加到模型中。

@SessionAttributes: 將模型中的某個屬性暫存到HttpSession 中,以便多個請求之間可以共享這個屬性

@ModelAttribute: 方法入參標注該注解后, 入參的對象就會放到數據模型中

二、ModelAndView

控制器處理方法的返回值如果為ModelAndView, 則其既包含視圖信息,也包含模型數據信息。

添加模型數據:

MoelAndView addObject(String attributeName,?Object attributeValue)

ModelAndView addAllObject(Map?modelMap)

設置視圖:

void setView(View?view)

void setViewName(String?viewName)

三、Map及Model

Spring MVC?在內部使用了一個org.springframework.ui.Model 接口存儲模型數據

具體步驟

Spring MVC?在調用方法前會創(chuàng)建一個隱含的模型對象作為模型數據的存儲容器。

如果方法的入參為Map?Model?類型,Spring MVC 會將隱含模型的引用傳遞給這些入參。在方法體內,開發(fā)者可以通過這個入參對象訪問到模型中的所有數據,也可以向模型中添加新的屬性數據

四、@SessionAttributes

若希望在多個請求之間共用某個模型屬性數據,則可以在控制器類上標注一@SessionAttributes, Spring?MVC 將在模型中對應的屬性暫存到HttpSession?中。

@SessionAttributes?除了可以通過屬性名指定需要放到會話中的屬性外,還可以通過模型屬性的對象類型指定哪些模型屬性需要放到會話中

@SessionAttributes(types=User.class) 會將隱含模型中所有類型為User.class 的屬性添加到會話中。

@SessionAttributes(value={“user1”,?“user2”})

@SessionAttributes(types={User.class,?Dept.class})

@SessionAttributes(value={“user1”,?“user2”}, types={Dept.class})

在類上面加上注解

五、@ModelAttribute

(1)在方法定義上使用@ModelAttribute?注解:Spring MVC在調用目標處理方法前,會先逐個調用在方法級上標注了@ModelAttribute 的方法。

(2)在方法的入參前使用@ModelAttribute?注解:

可以從隱含對象中獲取隱含的模型數據中獲取對象,再將請求參數

綁定到對象中,再傳入入參

– 將方法入參對象添加到模型中

(3)模擬修改操作

1、原始數據放在表單的value

2、密碼不能修改

3、表單回顯,模擬操作直接在表單填寫對應的屬性值

運行流程:

1、執(zhí)行@ModelAttribute注解修飾的方法:從數據庫中取出對象,把對象放入到了Map中,鍵為user

2、SpringMVC從Map中取出User對象,并把表單的請求參數賦給改User對象的對應屬性

3、SpringMVC把上述對象傳入目標方法的參數

在ModelAttribute修飾的方法中,放入到Map時的鍵需要和目標方法入參類型的第一個字母小寫的字符串一致!

源代碼分析的流程

1. 調用 @ModelAttribute 注解修飾的方法. 實際上把 @ModelAttribute 方法中 Map 中的數據放在了 implicitModel 中.

2. 解析請求處理器的目標參數, 實際上該目標參數來自于 WebDataBinder 對象的 target 屬性

1). 創(chuàng)建 WebDataBinder 對象:

①. 確定 objectName 屬性: 若傳入的 attrName 屬性值為 "", 則 objectName 為類名第一個字母小寫.

注意: attrName. 若目標方法的 POJO 屬性使用了 @ModelAttribute 來修飾, 則 attrName 值即為 @ModelAttribute的 value 屬性值

②. 確定 target 屬性:

> 在 implicitModel 中查找 attrName 對應的屬性值. 若存在, ok

?> *若不存在: 則驗證當前 Handler 是否使用了 @SessionAttributes 進行修飾, 若使用了, 則嘗試從 Session 中獲取 attrName 所對應的屬性值. 若 session 中沒有對應的屬性值, 則拋出了異常.

> 若 Handler 沒有使用 @SessionAttributes 進行修飾, 或 @SessionAttributes 中沒有使用 value 值指定的 key和 attrName 相匹配, 則通過反射創(chuàng)建了 POJO 對象

2). SpringMVC 把表單的請求參數賦給了 WebDataBinder 的 target 對應的屬性.

3). *SpringMVC 會把 WebDataBinder 的 attrName 和 target 給到 implicitModel,進而傳到 request 域對象中.

4). 把 WebDataBinder 的 target 作為參數傳遞給目標方法的入參.

SpringMVC 確定目標方法 POJO 類型入參的過程

* 1. 確定一個 key:

* 1). 若目標方法的 POJO 類型的參數木有使用 @ModelAttribute 作為修飾, 則 key 為 POJO 類名第一個字母的小寫

* 2). 若使用了? @ModelAttribute 來修飾, 則 key 為 @ModelAttribute 注解的 value 屬性值.

* 2. 在 implicitModel 中查找 key 對應的對象, 若存在, 則作為入參傳入

* 1). 若在 @ModelAttribute 標記的方法中在 Map 中保存過, 且 key 和 1 確定的 key 一致, 則會獲取到.

* 3. 若 implicitModel 中不存在 key 對應的對象, 則檢查當前的 Handler 是否使用 @SessionAttributes 注解修飾,

* 若使用了該注解, 且 @SessionAttributes 注解的 value 屬性值中包含了 key, 則會從 HttpSession 中來獲取 key 所

* 對應的 value 值, 若存在則直接傳入到目標方法的入參中. 若不存在則將拋出異常.

* 4. 若 Handler 沒有標識 @SessionAttributes 注解或 @SessionAttributes 注解的 value 值中不包含 key, 則

* 會通過反射來創(chuàng)建 POJO 類型的參數, 傳入為目標方法的參數

* 5. SpringMVC 會把 key 和 POJO 類型的對象保存到 implicitModel 中, 進而會保存到 request 中.

1. 有 @ModelAttribute 標記的方法, 會在每個目標方法執(zhí)行之前被 SpringMVC 調用!

2. @ModelAttribute 注解也可以來修飾目標方法 POJO 類型的入參, 其 value 屬性值有如下的作用:

* 1). SpringMVC 會使用 value 屬性值在 implicitModel 中查找對應的對象, 若存在則會直接傳入到目標方法的入參中.

* 2). SpringMVC 會一 value 為 key, POJO 類型的對象為 value, 存入到 request 中.

六、由@SessionAttributes引發(fā)的異常

如果在處理類定義處標注了@SessionAttributes(“xxx”),則嘗試從會話中獲取該屬性,并將其賦給該入參,然后再用請求消息填充該入參對象。如果在會話中找不到對應的屬性,則拋出HttpSessionRequiredException?異常

如何避免@SessionAttributes引發(fā)的異常

該方法會往隱含模型中添加一個名為user的模型屬性

?著作權歸作者所有,轉載或內容合作請聯(lián)系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發(fā)布,文章內容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌,老刑警劉巖,帶你破解...
    沈念sama閱讀 228,739評論 6 534
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異,居然都是意外死亡,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 98,634評論 3 419
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人,你說我怎么就攤上這事。” “怎么了?”我有些...
    開封第一講書人閱讀 176,653評論 0 377
  • 文/不壞的土叔 我叫張陵,是天一觀的道長。 經常有香客問我,道長,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 63,063評論 1 314
  • 正文 為了忘掉前任,我火速辦了婚禮,結果婚禮上,老公的妹妹穿的比我還像新娘。我一直安慰自己,他們只是感情好,可當我...
    茶點故事閱讀 71,835評論 6 410
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著,像睡著了一般。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 55,235評論 1 324
  • 那天,我揣著相機與錄音,去河邊找鬼。 笑死,一個胖子當著我的面吹牛,可吹牛的內容都是我干的。 我是一名探鬼主播,決...
    沈念sama閱讀 43,315評論 3 442
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 42,459評論 0 289
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后,有當地人在樹林里發(fā)現(xiàn)了一具尸體,經...
    沈念sama閱讀 49,000評論 1 335
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 40,819評論 3 355
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 43,004評論 1 370
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內的尸體忽然破棺而出,到底是詐尸還是另有隱情,我是刑警寧澤,帶...
    沈念sama閱讀 38,560評論 5 362
  • 正文 年R本政府宣布,位于F島的核電站,受9級特大地震影響,放射性物質發(fā)生泄漏。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 44,257評論 3 347
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 34,676評論 0 26
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 35,937評論 1 288
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人。 一個月前我還...
    沈念sama閱讀 51,717評論 3 393
  • 正文 我出身青樓,卻偏偏與公主長得像,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 48,003評論 2 374

推薦閱讀更多精彩內容