激情久久久_欧美视频区_成人av免费_不卡视频一二三区_欧美精品在欧美一区二区少妇_欧美一区二区三区的

服務(wù)器之家:專注于服務(wù)器技術(shù)及軟件下載分享
分類(lèi)導(dǎo)航

PHP教程|ASP.NET教程|Java教程|ASP教程|編程技術(shù)|正則表達(dá)式|C/C++|IOS|C#|Swift|Android|VB|R語(yǔ)言|JavaScript|易語(yǔ)言|vb.net|

服務(wù)器之家 - 編程語(yǔ)言 - Java教程 - Spring MVC入門(mén)_動(dòng)力節(jié)點(diǎn)Java學(xué)院整理

Spring MVC入門(mén)_動(dòng)力節(jié)點(diǎn)Java學(xué)院整理

2020-12-24 11:46張開(kāi)濤 Java教程

這篇文章主要介紹了Spring MVC入門(mén),小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧

spring web mvc是一種基于java的實(shí)現(xiàn)了web mvc設(shè)計(jì)模式的請(qǐng)求驅(qū)動(dòng)類(lèi)型的輕量級(jí)web框架,即使用了mvc架構(gòu)模式的思想,將web層進(jìn)行職責(zé)解耦,基于請(qǐng)求驅(qū)動(dòng)指的就是使用請(qǐng)求-響應(yīng)模型,框架的目的就是幫助我們簡(jiǎn)化開(kāi)發(fā),spring web mvc也是要簡(jiǎn)化我們?nèi)粘eb開(kāi)發(fā)的。另外還有一種基于組件的、事件驅(qū)動(dòng)的web框架在此就不介紹了,如tapestry、jsf等。

spring web mvc也是服務(wù)到工作者模式的實(shí)現(xiàn),但進(jìn)行可優(yōu)化。前端控制器是dispatcherservlet;應(yīng)用控制器其實(shí)拆為處理器映射器(handler mapping)進(jìn)行處理器管理和視圖解析器(view resolver)進(jìn)行視圖管理;頁(yè)面控制器/動(dòng)作/處理器為controller接口(僅包含modelandview handlerequest(request, response) 方法)的實(shí)現(xiàn)(也可以是任何的pojo類(lèi));支持本地化(locale)解析、主題(theme)解析及文件上傳等;提供了非常靈活的數(shù)據(jù)驗(yàn)證、格式化和數(shù)據(jù)綁定機(jī)制;提供了強(qiáng)大的約定大于配置(慣例優(yōu)先原則)的契約式編程支持。

spring web mvc能幫我們做什么

  • 讓我們能非常簡(jiǎn)單的設(shè)計(jì)出干凈的web層和薄薄的web層;
  • 進(jìn)行更簡(jiǎn)潔的web層的開(kāi)發(fā);
  • 天生與spring框架集成(如ioc容器、aop等);
  • 提供強(qiáng)大的約定大于配置的契約式編程支持;
  • 能簡(jiǎn)單的進(jìn)行web層的單元測(cè)試;
  • 支持靈活的url到頁(yè)面控制器的映射;
  • 非常容易與其他視圖技術(shù)集成,如velocity、freemarker等等,因?yàn)槟P蛿?shù)據(jù)不放在特定的api里,而是放在一個(gè)model里(map數(shù)據(jù)結(jié)構(gòu)實(shí)現(xiàn),因此很容易被其他框架使用);
  • 非常靈活的數(shù)據(jù)驗(yàn)證、格式化和數(shù)據(jù)綁定機(jī)制,能使用任何對(duì)象進(jìn)行數(shù)據(jù)綁定,不必實(shí)現(xiàn)特定框架的api;
  • 提供一套強(qiáng)大的jsp標(biāo)簽庫(kù),簡(jiǎn)化jsp開(kāi)發(fā);
  • 支持靈活的本地化、主題等解析;
  • 更加簡(jiǎn)單的異常處理;
  • 對(duì)靜態(tài)資源的支持;
  • 支持restful風(fēng)格。

spring web mvc架構(gòu)

spring web mvc框架也是一個(gè)基于請(qǐng)求驅(qū)動(dòng)的web框架,并且也使用了前端控制器模式來(lái)進(jìn)行設(shè)計(jì),再根據(jù)請(qǐng)求映射規(guī)則分發(fā)給相應(yīng)的頁(yè)面控制器(動(dòng)作/處理器)進(jìn)行處理。首先讓我們整體看一下spring web mvc處理請(qǐng)求的流程:

spring web mvc處理請(qǐng)求的流程

如圖2-1

Spring MVC入門(mén)_動(dòng)力節(jié)點(diǎn)Java學(xué)院整理

圖2-1

具體執(zhí)行步驟如下:

1、  首先用戶發(fā)送請(qǐng)求————>前端控制器,前端控制器根據(jù)請(qǐng)求信息(如url)來(lái)決定選擇哪一個(gè)頁(yè)面控制器進(jìn)行處理并把請(qǐng)求委托給它,即以前的控制器的控制邏輯部分;圖2-1中的1、2步驟;

2、  頁(yè)面控制器接收到請(qǐng)求后,進(jìn)行功能處理,首先需要收集和綁定請(qǐng)求參數(shù)到一個(gè)對(duì)象,這個(gè)對(duì)象在spring web mvc中叫命令對(duì)象,并進(jìn)行驗(yàn)證,然后將命令對(duì)象委托給業(yè)務(wù)對(duì)象進(jìn)行處理;處理完畢后返回一個(gè)modelandview(模型數(shù)據(jù)和邏輯視圖名);圖2-1中的3、4、5步驟;

3、  前端控制器收回控制權(quán),然后根據(jù)返回的邏輯視圖名,選擇相應(yīng)的視圖進(jìn)行渲染,并把模型數(shù)據(jù)傳入以便視圖渲染;圖2-1中的步驟6、7;

4、  前端控制器再次收回控制權(quán),將響應(yīng)返回給用戶,圖2-1中的步驟8;至此整個(gè)結(jié)束。

問(wèn)題:

1、  請(qǐng)求如何給前端控制器?
2、  前端控制器如何根據(jù)請(qǐng)求信息選擇頁(yè)面控制器進(jìn)行功能處理?
3、  如何支持多種頁(yè)面控制器呢?
4、  如何頁(yè)面控制器如何使用業(yè)務(wù)對(duì)象?
5、  頁(yè)面控制器如何返回模型數(shù)據(jù)?
6、  前端控制器如何根據(jù)頁(yè)面控制器返回的邏輯視圖名選擇具體的視圖進(jìn)行渲染?
7、  不同的視圖技術(shù)如何使用相應(yīng)的模型數(shù)據(jù)?

首先我們知道有如上問(wèn)題,那這些問(wèn)題如何解決呢?請(qǐng)讓我們先繼續(xù),在后邊依次回答。

spring web mvc架構(gòu)

1、spring web mvc核心架構(gòu)圖,如圖2-2

Spring MVC入門(mén)_動(dòng)力節(jié)點(diǎn)Java學(xué)院整理

圖2-2

架構(gòu)圖對(duì)應(yīng)的dispatcherservlet核心代碼如下:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
//前端控制器分派方法
protected void dodispatch(httpservletrequest request, httpservletresponse response) throws exception {
    httpservletrequest processedrequest = request;
    handlerexecutionchain mappedhandler = null;
    int interceptorindex = -1;
 
    try {
      modelandview mv;
      boolean errorview = false;
 
      try {
          //檢查是否是請(qǐng)求是否是multipart(如文件上傳),如果是將通過(guò)multipartresolver解析
        processedrequest = checkmultipart(request);
          //步驟2、請(qǐng)求到處理器(頁(yè)面控制器)的映射,通過(guò)handlermapping進(jìn)行映射
        mappedhandler = gethandler(processedrequest, false);
        if (mappedhandler == null || mappedhandler.gethandler() == null) {
          nohandlerfound(processedrequest, response);
          return;
        }
          //步驟3、處理器適配,即將我們的處理器包裝成相應(yīng)的適配器(從而支持多種類(lèi)型的處理器)
        handleradapter ha = gethandleradapter(mappedhandler.gethandler());
 
         // 304 not modified緩存支持
        //此處省略具體代碼
 
        // 執(zhí)行處理器相關(guān)的攔截器的預(yù)處理(handlerinterceptor.prehandle)
        //此處省略具體代碼
 
        // 步驟4、由適配器執(zhí)行處理器(調(diào)用處理器相應(yīng)功能處理方法)
        mv = ha.handle(processedrequest, response, mappedhandler.gethandler());
 
        // do we need view name translation?
        if (mv != null && !mv.hasview()) {
          mv.setviewname(getdefaultviewname(request));
        }
 
        // 執(zhí)行處理器相關(guān)的攔截器的后處理(handlerinterceptor.posthandle)
        //此處省略具體代碼
      }
      catch (modelandviewdefiningexception ex) {
        logger.debug("modelandviewdefiningexception encountered", ex);
        mv = ex.getmodelandview();
      }
      catch (exception ex) {
        object handler = (mappedhandler != null ? mappedhandlergethandler() : null);
        mv = processhandlerexception(processedrequest, response, handler, ex);
        errorview = (mv != null);
      }
 
      //步驟5 步驟6、解析視圖并進(jìn)行視圖的渲染
//步驟5 由viewresolver解析view(viewresolver.resolveviewname(viewname, locale))
//步驟6 視圖在渲染時(shí)會(huì)把model傳入(view.render(mv.getmodelinternal(), request, response);)
      if (mv != null && !mv.wascleared()) {
        render(mv, processedrequest, response);
        if (errorview) {
          webutils.clearerrorrequestattributes(request);
        }
      }
      else {
        if (logger.isdebugenabled()) {
          loggerdebug("null modelandview returned to dispatcherservlet with name '" + getservletname() +
              "': assuming handleradapter completed request handling");
        }
      }
 
      // 執(zhí)行處理器相關(guān)的攔截器的完成后處理(handlerinterceptor.aftercompletion)
      //此處省略具體代碼
 
 
    catch (exception ex) {
      // trigger after-completion for thrown exception
      triggeraftercompletion(mappedhandler, interceptorindex, processedrequest, response, ex);
      throw ex;
    }
    catch (error err) {
      servletexception ex = new nestedservletexception("handler processing failed", err);
      // trigger after-completion for thrown exception.
      triggeraftercompletion(mappedhandler, interceptorindex, processedrequest, response, ex);
      throw ex;
    }
 
    finally {
      // clean up any resources used by a multipart request
      if (processedrequest != request) {
        cleanupmultipart(processedrequest);
      }
    }
  }

核心架構(gòu)的具體流程步驟如下:

1、  首先用戶發(fā)送請(qǐng)求——>dispatcherservlet,前端控制器收到請(qǐng)求后自己不進(jìn)行處理,而是委托給其他的解析器進(jìn)行處理,作為統(tǒng)一訪問(wèn)點(diǎn),進(jìn)行全局的流程控制;

2、  dispatcherservlet——>handlermapping, handlermapping將會(huì)把請(qǐng)求映射為handlerexecutionchain對(duì)象(包含一個(gè)handler處理器(頁(yè)面控制器)對(duì)象、多個(gè)handlerinterceptor攔截器)對(duì)象,通過(guò)這種策略模式,很容易添加新的映射策略;

3、  dispatcherservlet——>handleradapter,handleradapter將會(huì)把處理器包裝為適配器,從而支持多種類(lèi)型的處理器,即適配器設(shè)計(jì)模式的應(yīng)用,從而很容易支持很多類(lèi)型的處理器;

4、  handleradapter——>處理器功能處理方法的調(diào)用,handleradapter將會(huì)根據(jù)適配的結(jié)果調(diào)用真正的處理器的功能處理方法,完成功能處理;并返回一個(gè)modelandview對(duì)象(包含模型數(shù)據(jù)、邏輯視圖名);

5、  modelandview的邏輯視圖名——> viewresolver, viewresolver將把邏輯視圖名解析為具體的view,通過(guò)這種策略模式,很容易更換其他視圖技術(shù);

6、  view——>渲染,view會(huì)根據(jù)傳進(jìn)來(lái)的model模型數(shù)據(jù)進(jìn)行渲染,此處的model實(shí)際是一個(gè)map數(shù)據(jù)結(jié)構(gòu),因此很容易支持其他視圖技術(shù);

7、返回控制權(quán)給dispatcherservlet,由dispatcherservlet返回響應(yīng)給用戶,到此一個(gè)流程結(jié)束。

此處我們只是講了核心流程,沒(méi)有考慮攔截器、本地解析、文件上傳解析等,后邊再細(xì)述。

到此,再來(lái)看我們前邊提出的問(wèn)題:

1、  請(qǐng)求如何給前端控制器?這個(gè)應(yīng)該在web.xml中進(jìn)行部署描述,在helloworld中詳細(xì)講解。
2、  前端控制器如何根據(jù)請(qǐng)求信息選擇頁(yè)面控制器進(jìn)行功能處理? 我們需要配置handlermapping進(jìn)行映射
3、  如何支持多種頁(yè)面控制器呢?配置handleradapter從而支持多種類(lèi)型的頁(yè)面控制器
4、  如何頁(yè)面控制器如何使用業(yè)務(wù)對(duì)象?可以預(yù)料到,肯定利用spring ioc容器的依賴注入功能
5、  頁(yè)面控制器如何返回模型數(shù)據(jù)?使用modelandview返回
6、  前端控制器如何根據(jù)頁(yè)面控制器返回的邏輯視圖名選擇具體的視圖進(jìn)行渲染? 使用viewresolver進(jìn)行解析
7、  不同的視圖技術(shù)如何使用相應(yīng)的模型數(shù)據(jù)? 因?yàn)閙odel是一個(gè)map數(shù)據(jù)結(jié)構(gòu),很容易支持其他視圖技術(shù)

在此我們可以看出具體的核心開(kāi)發(fā)步驟:

1、  dispatcherservlet在web.xml中的部署描述,從而攔截請(qǐng)求到spring web mvc
2、  handlermapping的配置,從而將請(qǐng)求映射到處理器
3、  handleradapter的配置,從而支持多種類(lèi)型的處理器
4、  viewresolver的配置,從而將邏輯視圖名解析為具體視圖技術(shù)
5、處理器(頁(yè)面控制器)的配置,從而進(jìn)行功能處理

上邊的開(kāi)發(fā)步驟我們會(huì)在hello world中詳細(xì)驗(yàn)證。

spring web mvc優(yōu)勢(shì)

1、清晰的角色劃分:前端控制器(dispatcherservlet)、請(qǐng)求到處理器映射(handlermapping)、處理器適配器(handleradapter)、視圖解析器(viewresolver)、處理器或頁(yè)面控制器(controller)、驗(yàn)證器(   validator)、命令對(duì)象(command  請(qǐng)求參數(shù)綁定到的對(duì)象就叫命令對(duì)象)、表單對(duì)象(form object 提供給表單展示和提交到的對(duì)象就叫表單對(duì)象)。
2、分工明確,而且擴(kuò)展點(diǎn)相當(dāng)靈活,可以很容易擴(kuò)展,雖然幾乎不需要;
3、由于命令對(duì)象就是一個(gè)pojo,無(wú)需繼承框架特定api,可以使用命令對(duì)象直接作為業(yè)務(wù)對(duì)象;
4、和spring 其他框架無(wú)縫集成,是其它web框架所不具備的;
5、可適配,通過(guò)handleradapter可以支持任意的類(lèi)作為處理器;
6、可定制性,handlermapping、viewresolver等能夠非常簡(jiǎn)單的定制;
7、功能強(qiáng)大的數(shù)據(jù)驗(yàn)證、格式化、綁定機(jī)制;
8、利用spring提供的mock對(duì)象能夠非常簡(jiǎn)單的進(jìn)行web層單元測(cè)試;
9、本地化、主題的解析的支持,使我們更容易進(jìn)行國(guó)際化和主題的切換。
10、強(qiáng)大的jsp標(biāo)簽庫(kù),使jsp編寫(xiě)更容易。

………………還有比如restful風(fēng)格的支持、簡(jiǎn)單的文件上傳、約定大于配置的契約式編程支持、基于注解的零配置支持等等。
到此我們已經(jīng)簡(jiǎn)單的了解了spring web mvc,接下來(lái)讓我們來(lái)個(gè)實(shí)例來(lái)具體使用下這個(gè)框架。

hello world入門(mén)

準(zhǔn)備開(kāi)發(fā)環(huán)境和運(yùn)行環(huán)境:

☆開(kāi)發(fā)工具:eclipse
☆運(yùn)行環(huán)境:tomcat6.0.20
☆工程:動(dòng)態(tài)web工程(springmvc-chapter2)
☆spring框架下載:
spring-framework-3.1.1.release-with-docs.zip

☆依賴jar包:

1、  spring框架jar包:
為了簡(jiǎn)單,將spring-framework-3.1.1.release-with-docs.zip/dist/下的所有jar包拷貝到項(xiàng)目的web-inf/lib目錄下;
2、  spring框架依賴的jar包:
需要添加apache commons logging日志,此處使用的是commons.logging-1.1.1.jar;
需要添加jstl標(biāo)簽庫(kù)支持,此處使用的是jstl-1.1.2.jar和standard-1.1.2.jar;
前端控制器的配置
在我們的web.xml中添加如下配置:

?
1
2
3
4
5
6
7
8
9
<servlet>
  <servlet-name>chapter2</servlet-name>
  <servlet-class>org.springframework.web.servlet.dispatcherservlet</servlet-class>
  <load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
  <servlet-name>chapter2</servlet-name>
  <url-pattern>/</url-pattern>
</servlet-mapping>

load-on-startup:表示啟動(dòng)容器時(shí)初始化該servlet;

url-pattern:表示哪些請(qǐng)求交給spring web mvc處理, “/” 是用來(lái)定義默認(rèn)servlet映射的。也可以如“*.html”表示攔截所有以html為擴(kuò)展名的請(qǐng)求。

自此請(qǐng)求已交給spring web mvc框架處理,因此我們需要配置spring的配置文件,默認(rèn)dispatcherservlet會(huì)加載web-inf/[dispatcherservlet的servlet名字]-servlet.xml配置文件。本示例為web-inf/ chapter2-servlet.xml。

在spring配置文件中配置handlermapping、handleradapter

具體配置在web-inf/ chapter2-servlet.xml文件中:

?
1
2
3
4
5
<!-- handlermapping -->
<bean class="org.springframework.web.servlet.handler.beannameurlhandlermapping"/>
 
<!-- handleradapter -->
<bean class="org.springframework.web.servlet.mvc.simplecontrollerhandleradapter"/>

beannameurlhandlermapping:表示將請(qǐng)求的url和bean名字映射,如url為 “上下文/hello”,則spring配置文件必須有一個(gè)名字為“/hello”的bean,上下文默認(rèn)忽略。

simplecontrollerhandleradapter:表示所有實(shí)現(xiàn)了org.springframework.web.servlet.mvc.controller接口的bean可以作為spring web mvc中的處理器。如果需要其他類(lèi)型的處理器可以通過(guò)實(shí)現(xiàn)hadleradapter來(lái)解決。

在spring配置文件中配置viewresolver

具體配置在web-inf/ chapter2-servlet.xml文件中:

?
1
2
3
4
5
6
<!-- viewresolver -->
<bean class="org.springframework.web.servlet.view.internalresourceviewresolver">
  <property name="viewclass" value="org.springframework.web.servlet.view.jstlview"/>
  <property name="prefix" value="/web-inf/jsp/"/>
  <property name="suffix" value=".jsp"/>
</bean>

internalresourceviewresolver:用于支持servlet、jsp視圖解析;

viewclass:jstlview表示jsp模板頁(yè)面需要使用jstl標(biāo)簽庫(kù),classpath中必須包含jstl的相關(guān)jar包;

prefix和suffix:查找視圖頁(yè)面的前綴和后綴(前綴[邏輯視圖名]后綴),比如傳進(jìn)來(lái)的邏輯視圖名為hello,則該該jsp視圖頁(yè)面應(yīng)該存放在“web-inf/jsp/hello.jsp”;

開(kāi)發(fā)處理器/頁(yè)面控制器

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
package com.bjpowernode.chapter2.web.controller;
import javax.servlet.http.httpservletrequest;
import javax.servlet.http.httpservletresponse;
import org.springframework.web.servlet.modelandview;
import org.springframework.web.servlet.mvc.controller;
public class helloworldcontroller implements controller {
  @override
  public modelandview handlerequest(httpservletrequest req, httpservletresponse resp) throws exception {
    //1、收集參數(shù)、驗(yàn)證參數(shù)
    //2、綁定參數(shù)到命令對(duì)象
    //3、將命令對(duì)象傳入業(yè)務(wù)對(duì)象進(jìn)行業(yè)務(wù)處理
    //4、選擇下一個(gè)頁(yè)面
    modelandview mv = new modelandview();
    //添加模型數(shù)據(jù) 可以是任意的pojo對(duì)象
    mv.addobject("message", "hello world!");
    //設(shè)置邏輯視圖名,視圖解析器會(huì)根據(jù)該名字解析到具體的視圖頁(yè)面
    mv.setviewname("hello");
    return mv;
  }
}

org.springframework.web.servlet.mvc.controller:頁(yè)面控制器/處理器必須實(shí)現(xiàn)controller接口,注意別選錯(cuò)了;后邊我們會(huì)學(xué)習(xí)其他的處理器實(shí)現(xiàn)方式;

public modelandview handlerequest(httpservletrequest req, httpservletresponse resp) :功能處理方法,實(shí)現(xiàn)相應(yīng)的功能處理,比如收集參數(shù)、驗(yàn)證參數(shù)、綁定參數(shù)到命令對(duì)象、將命令對(duì)象傳入業(yè)務(wù)對(duì)象進(jìn)行業(yè)務(wù)處理、最后返回modelandview對(duì)象;

modelandview:包含了視圖要實(shí)現(xiàn)的模型數(shù)據(jù)和邏輯視圖名;“mv.addobject("message", "hello world!");
”表示添加模型數(shù)據(jù),此處可以是任意pojo對(duì)象;“mv.setviewname("hello");”表示設(shè)置邏輯視圖名為“hello”,視圖解析器會(huì)將其解析為具體的視圖,如前邊的視圖解析器internalresourcevi。wresolver會(huì)將其解析為“web-inf/jsp/hello.jsp”。

我們需要將其添加到spring配置文件(web-inf/chapter2-servlet.xml),讓其接受spring ioc容器管理:

?
1
2
<!-- 處理器 -->
<bean name="/hello" class="com.bjpowernode.chapter2.web.controller.helloworldcontroller"/>

name="/hello":前邊配置的beannameurlhandlermapping,表示如過(guò)請(qǐng)求的url為 “上下文/hello”,則將會(huì)交給該bean進(jìn)行處理。 

開(kāi)發(fā)視圖頁(yè)面

創(chuàng)建 /web-inf/jsp/hello.jsp視圖頁(yè)面:

?
1
2
3
4
5
6
7
8
9
10
11
<%@ page language="java" contenttype="text/html; charset=utf-8" pageencoding="utf-8"%>
<!doctype html public "-//w3c//dtd html 4.01 transitional//en" "http://www.w3.org/tr/html4/loose.dtd">
<html>
<head>
<meta http-equiv="content-type" content="text/html; charset=utf-8">
<title>hello world</title>
</head>
<body>
${message}
</body>
</html>

${message}:表示顯示由helloworldcontroller處理器傳過(guò)來(lái)的模型數(shù)據(jù)。

啟動(dòng)服務(wù)器運(yùn)行測(cè)試

通過(guò)請(qǐng)求:http://localhost:9080/springmvc-chapter2/hello,如果頁(yè)面輸出“hello world! ”就表明我們成功了!

運(yùn)行流程分析

如圖2-3

Spring MVC入門(mén)_動(dòng)力節(jié)點(diǎn)Java學(xué)院整理

圖2-3

運(yùn)行步驟:

1、  首先用戶發(fā)送請(qǐng)求http://localhost:9080/springmvc-chapter2/hello——>web容器,web容器根據(jù)“/hello”路徑映射到dispatcherservlet(url-pattern為/)進(jìn)行處理;
2、  dispatcherservlet——>beannameurlhandlermapping進(jìn)行請(qǐng)求到處理的映射,beannameurlhandlermapping將“/hello”路徑直接映射到名字為“/hello”的bean進(jìn)行處理,即helloworldcontroller,beannameurlhandlermapping將其包裝為handlerexecutionchain(只包括helloworldcontroller處理器,沒(méi)有攔截器);
3、  dispatcherservlet——> simplecontrollerhandleradapter,simplecontrollerhandleradapter將handlerexecutionchain中的處理器(helloworldcontroller)適配為simplecontrollerhandleradapter;
4、  simplecontrollerhandleradapter——> helloworldcontroller處理器功能處理方法的調(diào)用,simplecontrollerhandleradapter將會(huì)調(diào)用處理器的handlerequest方法進(jìn)行功能處理,該處理方法返回一個(gè)modelandview給dispatcherservlet;
5、  hello(modelandview的邏輯視圖名)——>internalresourceviewresolver, internalresourceviewresolver使用jstlview,具體視圖頁(yè)面在/web-inf/jsp/hello.jsp;
6、  jstlview(/web-inf/jsp/hello.jsp)——>渲染,將在處理器傳入的模型數(shù)據(jù)(message=helloworld!)在視圖中展示出來(lái);
7、  返回控制權(quán)給dispatcherservlet,由dispatcherservlet返回響應(yīng)給用戶,到此一個(gè)流程結(jié)束。

到此helloworld就完成了,步驟是不是有點(diǎn)多?而且回憶下我們主要進(jìn)行了如下配置:

1、  前端控制器dispatcherservlet;
2、  handlermapping
3、  handleradapter
4、  viewresolver
5、  處理器/頁(yè)面控制器
6、  視圖

因此,接下來(lái)幾章讓我們?cè)敿?xì)看看這些配置,先從dispatcherservlet開(kāi)始吧。

post中文亂碼解決方案

spring web mvc框架提供了org.springframework.web.filter.characterencodingfilter用于解決post方式造成的中文亂碼問(wèn)題,具體配置如下:

?
1
2
3
4
5
6
7
8
9
10
11
12
<filter>
  <filter-name>characterencodingfilter</filter-name>
  <filter-class>org.springframework.web.filter.characterencodingfilter</filter-class>
  <init-param>
    <param-name>encoding</param-name>
    <param-value>utf-8</param-value>
  </init-param>
</filter>
<filter-mapping>
  <filter-name>characterencodingfilter</filter-name>
  <url-pattern>/*</url-pattern>
</filter-mapping>

以后我們項(xiàng)目及所有頁(yè)面的編碼均為utf-8。

spring3.1新特性

1.spring2.5之前,我們都是通過(guò)實(shí)現(xiàn)controller接口或其實(shí)現(xiàn)來(lái)定義我們的處理器類(lèi)。

2.spring2.5引入注解式處理器支持,通過(guò)@controller 和 @requestmapping注解定義我們的處理器類(lèi)。并且提供了一組強(qiáng)大的注解:

需要通過(guò)處理器映射defaultannotationhandlermapping和處理器適配器annotationmethodhandleradapter來(lái)開(kāi)啟支持@controller 和 @requestmapping注解的處理器。

@controller:用于標(biāo)識(shí)是處理器類(lèi);
@requestmapping:請(qǐng)求到處理器功能方法的映射規(guī)則;
@requestparam:請(qǐng)求參數(shù)到處理器功能處理方法的方法參數(shù)上的綁定;
@modelattribute:請(qǐng)求參數(shù)到命令對(duì)象的綁定;
@sessionattributes:用于聲明session級(jí)別存儲(chǔ)的屬性,放置在處理器類(lèi)上,通常列出模型屬性(如@modelattribute)對(duì)應(yīng)的名稱,則這些屬性會(huì)透明的保存到session中;
@initbinder:自定義數(shù)據(jù)綁定注冊(cè)支持,用于將請(qǐng)求參數(shù)轉(zhuǎn)換到命令對(duì)象屬性的對(duì)應(yīng)類(lèi)型;

3.spring3.0引入restful架構(gòu)風(fēng)格支持(通過(guò)@pathvariable注解和一些其他特性支持),且又引入了更多的注解支持:

@cookievalue:cookie數(shù)據(jù)到處理器功能處理方法的方法參數(shù)上的綁定;
@requestheader:請(qǐng)求頭(header)數(shù)據(jù)到處理器功能處理方法的方法參數(shù)上的綁定;
@requestbody:請(qǐng)求的body體的綁定(通過(guò)httpmessageconverter進(jìn)行類(lèi)型轉(zhuǎn)換);
@responsebody:處理器功能處理方法的返回值作為響應(yīng)體(通過(guò)httpmessageconverter進(jìn)行類(lèi)型轉(zhuǎn)換);
@responsestatus:定義處理器功能處理方法/異常處理器返回的狀態(tài)碼和原因;
@exceptionhandler:注解式聲明異常處理器;
@pathvariable:請(qǐng)求uri中的模板變量部分到處理器功能處理方法的方法參數(shù)上的綁定,從而支持restful架構(gòu)風(fēng)格的uri;

4.還有比如:

jsr-303驗(yàn)證框架的無(wú)縫支持(通過(guò)@valid注解定義驗(yàn)證元數(shù)據(jù));

使用spring 3開(kāi)始的conversionservice進(jìn)行類(lèi)型轉(zhuǎn)換(propertyeditor依然有效),支持使用@numberformat 和 @datetimeformat來(lái)進(jìn)行數(shù)字和日期的格式化;

httpmessageconverter(http輸入/輸出轉(zhuǎn)換器,比如json、xml等的數(shù)據(jù)輸出轉(zhuǎn)換器);

contentnegotiatingviewresolver,內(nèi)容協(xié)商視圖解析器,它還是視圖解析器,只是它支持根據(jù)請(qǐng)求信息將同一模型數(shù)據(jù)以不同的視圖方式展示(如json、xml、html等),restful架構(gòu)風(fēng)格中很重要的概念(同一資源,多種表現(xiàn)形式);

spring 3 引入 一個(gè)  mvc xml的命名空間用于支持mvc配置,包括如:

<mvc:annotation-driven>:

自動(dòng)注冊(cè)基于注解風(fēng)格的處理器需要的defaultannotationhandlermapping、annotationmethodhandleradapter

 支持spring3的conversionservice自動(dòng)注冊(cè)

支持jsr-303驗(yàn)證框架的自動(dòng)探測(cè)并注冊(cè)(只需把jsr-303實(shí)現(xiàn)放置到classpath)

自動(dòng)注冊(cè)相應(yīng)的httpmessageconverter(用于支持@requestbody  和 @responsebody)(如xml輸入輸出轉(zhuǎn)換器(只需將jaxp實(shí)現(xiàn)放置到classpath)、json輸入輸出轉(zhuǎn)換器(只需將jackson實(shí)現(xiàn)放置到classpath))等。

<mvc:interceptors>:注冊(cè)自定義的處理器攔截器;

<mvc:view-controller>:和parameterizableviewcontroller類(lèi)似,收到相應(yīng)請(qǐng)求后直接選擇相應(yīng)的視圖;

<mvc:resources>:邏輯靜態(tài)資源路徑到物理靜態(tài)資源路徑的支持;

 <mvc:default-servlet-handler>:當(dāng)在web.xml 中dispatcherservlet使用<url-pattern>/</url-pattern> 映射時(shí),能映射靜態(tài)資源(當(dāng)spring web mvc框架沒(méi)有處理請(qǐng)求對(duì)應(yīng)的控制器時(shí)(如一些靜態(tài)資源),轉(zhuǎn)交給默認(rèn)的servlet來(lái)響應(yīng)靜態(tài)文件,否則報(bào)404找不到資源錯(cuò)誤,)。

……等等。

6.spring3.1新特性:

對(duì)servlet 3.0的全面支持。

@enablewebmvc:用于在基于java類(lèi)定義bean配置中開(kāi)啟mvc支持,和xml中的<mvc:annotation-driven>功能一樣;

新的@contoller和@requestmapping注解支持類(lèi):處理器映射requestmappinghandlermapping 和 處理器適配器requestmappinghandleradapter組合來(lái)代替spring2.5開(kāi)始的處理器映射defaultannotationhandlermapping和處理器適配器annotationmethodhandleradapter,提供更多的擴(kuò)展點(diǎn),它們之間的區(qū)別我們?cè)谔幚砥饔成湟徽陆榻B。

新的@exceptionhandler 注解支持類(lèi):exceptionhandlerexceptionresolver來(lái)代替spring3.0的annotationmethodhandlerexceptionresolver,在異常處理器一章我們?cè)僭敿?xì)講解它們的區(qū)別。

@requestmapping的"consumes" 和 "produces" 條件支持:用于支持@requestbody 和 @responsebody,

1consumes指定請(qǐng)求的內(nèi)容是什么類(lèi)型的內(nèi)容,即本處理方法消費(fèi)什么類(lèi)型的數(shù)據(jù),如consumes="application/json"表示json類(lèi)型的內(nèi)容,spring會(huì)根據(jù)相應(yīng)的httpmessageconverter進(jìn)行請(qǐng)求內(nèi)容區(qū)數(shù)據(jù)到@requestbody注解的命令對(duì)象的轉(zhuǎn)換;

2produces指定生產(chǎn)什么類(lèi)型的內(nèi)容,如produces="application/json"表示json類(lèi)型的內(nèi)容,spring的根據(jù)相應(yīng)的httpmessageconverter進(jìn)行請(qǐng)求內(nèi)容區(qū)數(shù)據(jù)到@requestbody注解的命令對(duì)象的轉(zhuǎn)換,spring會(huì)根據(jù)相應(yīng)的httpmessageconverter進(jìn)行模型數(shù)據(jù)(返回值)到j(luò)son響應(yīng)內(nèi)容的轉(zhuǎn)換

3以上內(nèi)容,本章第×××節(jié)詳述。

uri模板變量增強(qiáng):uri模板變量可以直接綁定到@modelattribute指定的命令對(duì)象、@pathvariable方法參數(shù)在視圖渲染之前被合并到模型數(shù)據(jù)中(除json序列化、xml混搭場(chǎng)景下)。

@validated:jsr-303的javax.validation.valid一種變體(非jsr-303規(guī)范定義的,而是spring自定義的),用于提供對(duì)spring的驗(yàn)證器(org.springframework.validation.validator)支持,需要hibernate validator 4.2及更高版本支持;

@requestpart:提供對(duì)“multipart/form-data”請(qǐng)求的全面支持,支持servlet 3.0文件上傳(javax.servlet.http.part)、支持內(nèi)容的httpmessageconverter(即根據(jù)請(qǐng)求頭的content-type,來(lái)判斷內(nèi)容區(qū)數(shù)據(jù)是什么類(lèi)型,如json、xml,能自動(dòng)轉(zhuǎn)換為命令對(duì)象),比@requestparam更強(qiáng)大(只能對(duì)請(qǐng)求參數(shù)數(shù)據(jù)綁定,key-alue格式),而@requestpart支持如json、xml內(nèi)容區(qū)數(shù)據(jù)的綁定;詳見(jiàn)本章的第×××節(jié);

flash 屬性 和 redirectattribute:通過(guò)flashmap存儲(chǔ)一個(gè)請(qǐng)求的輸出,當(dāng)進(jìn)入另一個(gè)請(qǐng)求時(shí)作為該請(qǐng)求的輸入,典型場(chǎng)景如重定向(post-redirect-get模式,1、post時(shí)將下一次需要的數(shù)據(jù)放在flashmap;2、重定向;3、通過(guò)get訪問(wèn)重定向的地址,此時(shí)flashmap會(huì)把1放到flashmap的數(shù)據(jù)取出放到請(qǐng)求中,并從flashmap中刪除;從而支持在兩次請(qǐng)求之間保存數(shù)據(jù)并防止了重復(fù)表單提交)。

spring web mvc提供flashmapmanager用于管理flashmap,默認(rèn)使用sessionflashmapmanager,即數(shù)據(jù)默認(rèn)存儲(chǔ)在session中。

延伸 · 閱讀

精彩推薦
主站蜘蛛池模板: 欧美黄色三级视频 | 久久免费精品视频 | 成人三级电影在线 | 国产精品区一区二区三区 | 一级电影免费在线观看 | 91情侣在线偷精品国产 | 李宗瑞国产福利视频一区 | 一本视频在线观看 | 亚洲免费在线看 | 激情综合网俺也去 | 国产午夜精品一区二区三区嫩草 | 一级黄色免费观看 | 亚州综合一区 | a黄在线观看| 久久国产精品久久久久久久久久 | 免费观看一级 | 久草在线高清视频 | 亚洲天堂中文字幕在线观看 | 久久久久久久99 | 国产免费观看一区二区三区 | 久草在线综合网 | xxxxhdvideosex| 一级网站| 日本在线播放一区二区三区 | 成人免费入口 | 精品一区二区免费视频视频 | 伊人在线视频 | 一级片a | 久久线视频 | 国产一区二区三区四区精 | chinese-xvideos | 免费午夜视频在线观看 | 国产高潮失禁喷水爽到抽搐视频 | 香蕉久久久久 | 麻豆porn| 美国一级黄色毛片 | 天天草天天干天天射 | 欧美亚洲一区二区三区四区 | 九色成人在线 | 一区二区三区欧美精品 | 91麻豆精品国产91久久久更新资源速度超快 |