一、Controller應該是SpringMVC的核心,Controller中要學習的註解也是多之又多,不過這些註解在程序中的做用確實不可小覷,看看列出這幾項:
html
@Controller : 定義一個類爲控制器,這個與 @Repository 有點像java
@RequestMapping : 定義Controller的URL映射以及請求方法node
@PathVariable : 定義路徑參數,Rest自己就是把資源進行惟必定義,那麼URL中使用參數也是惟必定義的一種形式web
@ResponseBody : 定義返回結果,這個在ajax請求的時候特別有用,由於不須要跳轉到其餘URLajax
@ResponseStatus : 定義返回狀態spring
@RequestParam : 定義請求參數,若是是前臺與後臺同名參數,那麼不必使用它數據庫
........................json
下面貼出Controller的代碼
api
/** * <p>項目名稱:restful * <p>Package名稱:com.hnust.controller * 文件名稱:ResourceController.java * 版本:1.00 * 建立日期:2014年10月26日 * Copyright©2014 HNUST .All Rights Reserved. */ package com.hnust.controller; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Controller; import org.springframework.ui.ModelMap; import org.springframework.util.StringUtils; import org.springframework.web.bind.annotation.PathVariable; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestMethod; import org.springframework.web.bind.annotation.ResponseBody; import com.hnust.bean.Message; import com.hnust.bean.Resource; import com.hnust.service.ResourceService; /** * *@author:Heweipo *@version 1.00 * */ @Controller @RequestMapping("/resource") public class ResourceController { @Autowired private ResourceService service; /** * * <p>經過id獲取資源 * 在這裏採用@PathVariable註解,同時返回一個String,讓SpringMVC自動尋找最合適的視圖解析器 * 優勢是可以找到html視圖解析器,可是缺點是,JavaBean轉爲XML格式, * 須要在 org.springframework.oxm.jaxb.Jaxb2Marshaller綁定JavaBean * 因此 這裏Resource必定要進行綁定 * @param id * @param model * @return * @return String * author: Heweipo */ @RequestMapping(value="/get/{id}" , method=RequestMethod.GET) public String get(@PathVariable("id") String id , ModelMap model){ model.put("resource", service.getResource(id)); return "resource"; } /** * * <p>存儲resource,另外,關於resource的number參數注入很值得注意,若是URL中攜帶的參數不能轉爲 * Integer類型,那麼是沒法繼續訪問這個方法的!!因此,對於JavaBean最好設置與數據庫對應的數據類型 * 進行類型約束。 * 在這裏採用@ResponseBody註解,那麼返回的對象將會被對應的視圖解析器解析, * 可是不會有html解析器,可是有一個 * 優勢:javaBean 若是轉爲 XML 是不須要在spring-servlet 中 * org.springframework.oxm.jaxb.Jaxb2Marshaller 綁定的 * @param resource * @param model * @return void * author: Heweipo */ @RequestMapping(value="/put" , method=RequestMethod.PUT) public @ResponseBody Message put(Resource resource , ModelMap model){ Message message = new Message(); if(StringUtils.isEmpty(resource.getId()) || StringUtils.isEmpty(resource.getName())){ message.setMsg("請輸入id 和 用戶名"); message.setResult("faile"); return message; } service.insertResource(resource); message.setMsg("數據已經存儲"); message.setResult("success"); return message; } /** * * <p>經過id更新resource * @param resource * @param model * @return * @return Message * author: Heweipo */ @RequestMapping(value="/post" , method=RequestMethod.POST) public @ResponseBody Message post(Resource resource , ModelMap model){ Message message = new Message(); if(StringUtils.isEmpty(resource.getId())){ message.setMsg("id不能爲空"); message.setResult("faile"); return message; } service.updateResource(resource); message.setMsg("數據已經修改"); message.setResult("success"); return message; } /** * * <p>經過id刪除資源 * @param id * @param model * @return * @return Message * author: Heweipo */ @RequestMapping(value="/delete/{id}" , method=RequestMethod.DELETE) public @ResponseBody Message delete(@PathVariable("id")String id, ModelMap model){ Message message = new Message(); service.deleteResource(id); message.setMsg("數據已刪除"); message.setResult("success"); return message; } }
注意的幾點說明:restful
1)關於請求參數自動封裝問題,當咱們在方法的形參中採用JavaBean時,SpringMVC會把請求的參數中與JavaBean對應的屬性封裝成JavaBean的一個實例返回,若是有些屬性沒有值,他就爲空;若是屬性值進行賦值是類型轉換髮生錯誤,則沒法請求URL。封裝好的JavaBean實例會存儲在ModelMap中,而且以JavaBean的類名首字母小寫的形式做爲key值,因此,你能夠 這樣獲取 model.get('resource');實際這也是很經常使用的,由於 XML解析的時候須要一個根元素,那麼,若是咱們的model中存儲太多的元素XML是沒法解析的。這個Controller不存在這種狀況,緣由是我是用了@ResponseBody
2)關於返回值的問題,@ResponseBody 是返回值的標識,尤爲是對象解析的時候特別有用。並且,使用@ResponseBody後,對於XML解析的對象均可以不用在spring-servlet中進行綁定,然而,若是咱們有些時候須要返回一個html,或者Json,或者XML的時候,咱們就不會去使用@ResponseBody,而是採用String的形式,把返回的對象存儲在model中。當返回值爲null時效果與@ResponseBody 是同樣的。
下面是修改後的代碼:
/** * * <p>經過id更新resource * Message 必定要在 org.springframework.oxm.jaxb.Jaxb2Marshaller 綁定 * @param resource * @param model * @return * @return Message * author: Heweipo */ @RequestMapping(value="/post" , method=RequestMethod.POST) public String post(Resource resource , ModelMap model){ // 這裏清除掉SpringMVC幫咱們封裝的JavaBean model.remove("resource"); Message message = new Message(); // 這裏存儲咱們須要解析的JavaBean model.put("message", message); if(StringUtils.isEmpty(resource.getId())){ message.setMsg("id不能爲空"); message.setResult("faile"); return null; } service.updateResource(resource); message.setMsg("數據已經修改"); message.setResult("success"); // 返回空的效果和使用@ResponseBody是同樣的,可是原理不一樣, // @ResponseBody 貌似採用了Servlet3.0 的異步特性 return null; }
對應的spring-servlet.xml源代碼:
<!-- XML 與 Java 數據轉換 --> <bean id="jaxbMarshaller" class="org.springframework.oxm.jaxb.Jaxb2Marshaller"> <property name="classesToBeBound"> <list> <!-- 須要在這裏綁定,緣由是controller裏沒有采用@ResponseBody進行返回 --> <value>com.hnust.bean.Message</value> </list> </property> </bean>
2 請求類型
在@RequestMapping中咱們對method進行賦值,若是賦值了那麼必須按照對應的請求方法進行訪問,否者出現405.該項目中採用測試工具進行測試:
工具採用:Firefox 的RestClient 插件 https://addons.mozilla.org/zh-CN/firefox/addon/restclient/
1)新增資源:put http://localhost:8080/restful/resource/put?id=id_888&name=ireport&number=89
<message> <msg>數據已經存儲</msg> <result>success</result> </message>
2)更新資源 post http://localhost:8080/restful/resource/post?id=id_888&name=node.js&number=12
<message> <msg>數據已經更新</msg> <result>success</result> </message>
3) 刪除資源 delete http://localhost:8080/restful/resource/delete/id_888
<message> <msg>數據已刪除</msg> <result>success</result> </message>
3 關於返回內容格式
內容協商機制很簡單,有兩種方式,一種是該項目中使用的視圖渲染進行內容協商,另一種則是進行類型轉換,本項目中源碼以下:
<!-- 主要是進行Controller 和 URL 的一些註解綁定,這裏能夠進行轉換器配置:只有配置好了轉換器才能進行類與JSON和XML的轉換,固然只是針對基於轉換器協商資源表述 --> <bean class="org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter" /> <!-- XML 與 Java 數據轉換 --> <bean id="jaxbMarshaller" class="org.springframework.oxm.jaxb.Jaxb2Marshaller"> <property name="classesToBeBound"> <list> <!--common XML 映射 JavaBean 註冊 --> <value>com.hnust.bean.Resource</value> <!-- 不須要在這裏綁定,緣由是controller裏採用ResponseBody進行返回 --> <!-- <value>com.hnust.bean.Message</value> --> </list> </property> </bean> <!-- 基於視圖渲染進行協商資源表述 --> <bean class="org.springframework.web.servlet.view.ContentNegotiatingViewResolver"> <!-- restful 是否採用擴展名的方式肯定內容格式,id.json 返回JSON格式 --> <property name="favorPathExtension" value="true"></property> <!-- restful 是否採用參數支持肯定內容格式,id?format=json 返回JSON格式 --> <property name="favorParameter" value="true"></property> <!-- restful 是否忽略掉accept header,Accept:application/json --> <property name="ignoreAcceptHeader" value="false"></property> <!-- 基於視圖按順序解析 --> <property name="order" value="1" /> <!-- 對採用擴展名,參數新式的 URL 進行獲取對應的 accept --> <property name="mediaTypes"> <map> <entry key="json" value="application/json"/> <entry key="xml" value="application/xml"/> <entry key="html" value="text/html"/> </map> </property> <!-- 若是擴展名,參數甚至header 信息都沒有找到對應的accept時 --> <property name="defaultContentType" value="text/html"/> <!-- 採用對應的視圖進行渲染 --> <property name="defaultViews"> <list > <!-- 轉換Java對象爲XML格式數據 --> <bean class="org.springframework.web.servlet.view.xml.MarshallingView"> <constructor-arg ref="jaxbMarshaller" /> </bean> <!-- 轉換Java對象爲JSON 格式數據 --> <bean class="org.springframework.web.servlet.view.json.MappingJacksonJsonView"/> </list> </property> <!-- 採用對應的視圖進行渲染 --> <property name="viewResolvers"> <list > <!-- 查找在上下文中定義了ID的Bean,而且定位該ID --> <bean class="org.springframework.web.servlet.view.BeanNameViewResolver"/> <!-- 對Controller中返回的視圖實例進行解析,而且組裝URL定位到對應的資源 --> <bean id="viewResolver" class="org.springframework.web.servlet.view.UrlBasedViewResolver"> <property name="viewClass" value="org.springframework.web.servlet.view.JstlView"/> <property name="prefix" value="/WEB-INF/jsp/"/> <property name="suffix" value=".jsp"/> </bean> </list> </property> </bean>
然而若是使用轉換機制的話:
<!-- 輸出字符串內容,非路徑 --> <bean id="stringConverter" class="org.springframework.http.converter.StringHttpMessageConverter"> <property name="supportedMediaTypes"> <list> <value>text/plain;charset=UTF-8</value> </list> </property> </bean> <!-- JSON --> <bean id="jsonConverter" class="org.springframework.http.converter.json.MappingJacksonHttpMessageConverter"></bean> <bean id="marshallingHttpMessageConverter" class="org.springframework.http.converter.xml.MarshallingHttpMessageConverter"> <constructor-arg ref="jaxbMarshaller"/> <property name="supportedMediaTypes" value="application/xml" /> </bean> <!-- 基於轉換器進行內容協商 --> <bean id="jaxbMarshaller" class="org.springframework.oxm.jaxb.Jaxb2Marshaller"> <!-- XML轉換器須要綁定須要轉換的類 --> <property name="classesToBeBound"> <list> <value>com.hnust.bean.Resource</value> </list> </property> </bean> <!-- 註冊對象轉換器 --> <bean class="org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter"> <property name="messageConverters"> <list> <ref bean="stringConverter" /> <ref bean="jsonConverter" /> <ref bean="marshallingHttpMessageConverter"/> </list> </property> </bean>
4 pom文件,獲取jar包
<dependency> <groupId>org.springframework</groupId> <artifactId>spring-web</artifactId> <version>3.2.8.RELEASE</version> </dependency> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-webmvc</artifactId> <version>3.2.8.RELEASE</version> </dependency> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-oxm</artifactId> <version>3.2.8.RELEASE</version> </dependency> <dependency> <groupId>javax.servlet</groupId> <artifactId>jstl</artifactId> <version>1.2</version> </dependency> <dependency> <groupId>log4j</groupId> <artifactId>log4j</artifactId> <version>1.2.17</version> </dependency> <dependency> <groupId>commons-logging</groupId> <artifactId>commons-logging</artifactId> <version>1.1.3</version> </dependency> <dependency> <groupId>net.sf.json-lib</groupId> <artifactId>json-lib</artifactId> <version>2.4</version> <classifier>jdk15</classifier> </dependency> <dependency> <groupId>org.codehaus.jackson</groupId> <artifactId>jackson-mapper-asl</artifactId> <version>1.9.13</version> </dependency> <dependency> <groupId>javax.servlet</groupId> <artifactId>servlet-api</artifactId> <version>3.0-alpha-1</version> </dependency>
5 項目源碼連接:
http://download.csdn.net/detail/wp562846864/8113077
說明:源碼中沒有jar包,由於Maven項目,jar包就經過pom文件去取吧,若是實在須要,能夠留言.....