1)REST具体表现:

--- /account/1  HTTP GET       获取id=1的account

--- /account/1  HTTP DELETE 删除id=1的account

--- /aacount/1  HTTP PUT        更新id=1的account

--- /account      HTTP POST     新增account

2)SpringMVC中如何实现REST?

众所周知,浏览器form表单只支持GET与POST请求,而DELETE、PUT等method并不支持。Spring3.0增加了一个过滤器,可以将这些请求转化为标准的http方法,使得支持GET、POST、PUT及DELETE请求。

这个过滤器就是:org.springframework.web.filter.HiddenHttpMethodFilter

 package org.springframework.web.filter;

 import java.io.IOException;
import java.util.Locale;
import javax.servlet.FilterChain;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletRequestWrapper;
import javax.servlet.http.HttpServletResponse; import org.springframework.util.Assert;
import org.springframework.util.StringUtils;
import org.springframework.web.util.WebUtils; /**
* {@link javax.servlet.Filter} that converts posted method parameters into HTTP methods,
* retrievable via {@link HttpServletRequest#getMethod()}. Since browsers currently only
* support GET and POST, a common technique - used by the Prototype library, for instance -
* is to use a normal POST with an additional hidden form field ({@code _method})
* to pass the "real" HTTP method along. This filter reads that parameter and changes
* the {@link HttpServletRequestWrapper#getMethod()} return value accordingly.
*
* <p>The name of the request parameter defaults to {@code _method}, but can be
* adapted via the {@link #setMethodParam(String) methodParam} property.
*
* <p><b>NOTE: This filter needs to run after multipart processing in case of a multipart
* POST request, due to its inherent need for checking a POST body parameter.</b>
* So typically, put a Spring {@link org.springframework.web.multipart.support.MultipartFilter}
* <i>before</i> this HiddenHttpMethodFilter in your {@code web.xml} filter chain.
*
* @author Arjen Poutsma
* @author Juergen Hoeller
* @since 3.0
*/
public class HiddenHttpMethodFilter extends OncePerRequestFilter { /** Default method parameter: {@code _method} */
public static final String DEFAULT_METHOD_PARAM = "_method"; private String methodParam = DEFAULT_METHOD_PARAM; /**
* Set the parameter name to look for HTTP methods.
* @see #DEFAULT_METHOD_PARAM
*/
public void setMethodParam(String methodParam) {
Assert.hasText(methodParam, "'methodParam' must not be empty");
this.methodParam = methodParam;
} @Override
protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain)
throws ServletException, IOException { HttpServletRequest requestToUse = request; if ("POST".equals(request.getMethod()) && request.getAttribute(WebUtils.ERROR_EXCEPTION_ATTRIBUTE) == null) {
String paramValue = request.getParameter(this.methodParam);
if (StringUtils.hasLength(paramValue)) {
requestToUse = new HttpMethodRequestWrapper(request, paramValue);
}
} filterChain.doFilter(requestToUse, response);
} /**
* Simple {@link HttpServletRequest} wrapper that returns the supplied method for
* {@link HttpServletRequest#getMethod()}.
*/
private static class HttpMethodRequestWrapper extends HttpServletRequestWrapper { private final String method; public HttpMethodRequestWrapper(HttpServletRequest request, String method) {
super(request);
this.method = method.toUpperCase(Locale.ENGLISH);
} @Override
public String getMethod() {
return this.method;
}
} }

从这个filter代码中可以得知,该filter是通过POST方式提交表单,该表单中包含一个名称为_method的隐藏域,该隐藏域的值用来判定将要转化的请求方式。所谓的转化请求方式,就是在该filter中重新生成了一个新的、标准化的请求。

3)如何使用到springmvc项目中?

步骤一:在web.xml中添加filter配置:

    <filter>
<filter-name>HiddenHttpMethodFilter</filter-name>
<filter-class>org.springframework.web.filter.HiddenHttpMethodFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>HiddenHttpMethodFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>

步骤二:在HelloWord.java中添加get/post/put/delete方法:

 package com.dx.springlearn.handlers;

 import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod; @Controller
@RequestMapping("class_requestmapping")
public class HelloWord {
private static String SUCCESS = "success"; @RequestMapping(value = "/accountDelete/{id}", method = RequestMethod.DELETE)
public String accountDelete(@PathVariable("id") Integer id) {
System.out.println("test rest DELETE,account id:" + id);
return SUCCESS;
} @RequestMapping(value = "/accountPut/{id}", method = RequestMethod.PUT)
public String accountPut(@PathVariable("id") Integer id) {
System.out.println("test rest PUT,account id:" + id);
return SUCCESS;
} @RequestMapping(value = "/account", method = RequestMethod.POST)
public String account() {
System.out.println("test rest POST");
return SUCCESS;
} @RequestMapping(value = "/account/{id}", method = RequestMethod.GET)
public String account(@PathVariable("id") Integer id) {
System.out.println("test rest GET,account id:" + id);
return SUCCESS;
}
}

步骤三:在index.jsp中添加get/post/put/delete方法请求的html脚本:

    <!-- delete提交 -->
<form id="form_testRestMethod_DELETE" name="form_testRestMethod_DELETE" method="POST"
action="class_requestmapping/accountDelete/2">
<input type="hidden" name="_method" value="DELETE" />
<button name="submit" id="submit">test rest DELETE</button>
</form>
<br>
<!-- put提交 -->
<form id="form_testRestMethod_PUT" name="form_testRestMethod_PUT" method="POST"
action="class_requestmapping/accountPut/2">
<input type="hidden" name="_method" value="PUT" />
<button name="submit" id="submit">test rest PUT</button>
</form>
<br>
<!-- post提交 -->
<form id="form_testRestMethod_POST" name="form_testRestMethod_POST"
method="POST" action="class_requestmapping/account">
<button name="submit" id="submit">test rest POST</button>
</form>
<br>
<!-- get提交 -->
<a href="class_requestmapping/account/1">test rest GET</a>
<br>

步骤四:测试打印结果为:

test rest GET,account id:1
test rest POST
test rest PUT,account id:2
test rest DELETE,account id:2

SpringMVC(四):@RequestMapping结合org.springframework.web.filter.HiddenHttpMethodFilter实现REST请求的更多相关文章

  1. SpringMVC(四) RequestMapping请求方式

    常见的Rest API的Get和POST的测试参考代码如下,其中web.xml和Springmvc的配置文件参考HelloWorld测试代码中的配置. 控制类的代码如下: package com.ti ...

  2. java.lang.ClassCastException: org.springframework.web.filter.CharacterEncodingFilter cannot be cast

    严重: Exception starting filter encodingFilterjava.lang.ClassCastException: org.springframework.web.fi ...

  3. java.lang.ClassNotFoundException: org.springframework.web.filter.CharacterEncodingFilter

    今天在用git merge 新代码后报了如下错误:java.lang.ClassNotFoundException: org.springframework.web.filter.CharacterE ...

  4. org.springframework.web.filter.CharacterEncodingFilter

    感谢:http://blog.csdn.net/heidan2006/article/details/3075730 很简单很实用的一个过滤器,当前台JSP页面和JAVA代码中使用了不同的字符集进行编 ...

  5. 通过org.springframework.web.filter.CharacterEncodingFilter定义Spring web请求的编码

    通过类org.springframework.web.filter.CharacterEncodingFilter,定义request和response的编码.具体做法是,在web.xml中定义一个F ...

  6. org.springframework.web.filter.DelegatingFilterProxy的理解

    org.springframework.web.filter.DelegatingFilterProxy可以将filter交给spring管理. 我们web.xml中配置filter时一般采用下面这种 ...

  7. java.lang.ClassCastException: org.springframework.web.filter.CharacterEncodingFilter cannot be cast to javax.servlet.Filter

    java.lang.ClassCastException: org.springframework.web.filter.CharacterEncodingFilter cannot be cast ...

  8. org.springframework.web.filter.DelegatingFilterProxy的作用

    一.类结构 DelegatingFilterProxy类继承GenericFilterBean,间接实现了Filter,故而该类属于一个过滤器.那么就会有实现Filter中init.doFilter. ...

  9. Caused by: java.lang.ClassNotFoundException: org.springframework.web.filter.FormContentFilter

    又是一个报错,我写代码真的是可以,所有的bug都会被我遇到,所有的问题我都能踩一遍,以前上学的时候同学就喜欢问我问题,因为他们遇到的问题,我早就遇到了......... 看看报错内容: 2019-04 ...

随机推荐

  1. Database operations of Mysql

    update 表名 set 字段名=replace(同一个字段名,原字符串,新字符串);  --修改记录. 一.初始化 # cd /usr/local/mysql # chown -R mysql:m ...

  2. FastJson简单使用

    首先建立两个实体类,Student.java 和 Teacher.java public class Student { private int id; private String name; pr ...

  3. JS常用函数用途小记

    concat() 方法用于连接两个或多个数组. 该方法不会改变现有的数组,而仅仅会返回被连接数组的一个副本. var a = [1,2,3]; document.write(a.concat(4,5) ...

  4. JavaIO

    1.字节流和字符流 在IO有两种数据传输格式一个是字符流还一个是字节流,但是字符流就会涉及到编码的问题. 一开始美国使用的自己的编码表就是ASCII表 中国的字符需要被识别也需要编码表于是就有了GB2 ...

  5. 数据库 --> MySQL使用

    MySQL使用 代码: #include <sys/types.h> #include <sys/stat.h> #include <fcntl.h>#includ ...

  6. 一次精疲力尽的改bug经历

    一.介绍 最近一直在做有关JavaScriptCore的技术需求,上周发现一个问题,当在JavaScriptCore在垃圾回收时,项目会有一定几率发生崩溃.崩溃发生时调用堆栈如下: 图1 调用堆栈 先 ...

  7. [poj1068]Parencodings_模拟

    Parencodings 题目大意:给你一个P序列,表示从左到右的右括号左边有多少左括号,求M序列. 注释:M序列定义为每一个右括号左边最近的没有被之前的右括号匹配的括号之间,有多少已经匹配的括号队对 ...

  8. 实现Windows程序的数据绑定

    1.创建DataSet对象 语法: DataSet  数据集对象  =new  DataSet("数据集的名称字符串"); 语法中的参数是数据集的名称字符串,可以有,也可以没有.如 ...

  9. Access数据库跨库查询及记录集区分

    医疗设备软件一般都是单机软件,如果是Windows平台,常会选择Access数据库存储结构化数据,因为他轻量,便于部署.然而随着医疗信息化的发展,医生希望对多台单机设备的数据进行管理,采用网络数据库当 ...

  10. 软工实践项目需求分析(团队)修改版get√-黄紫仪

    日常前言:随笔距离文档大体完成已经过去了2天+(因为中间插了一波结对作业),所以目测感受没有那时候清晰(那时候烦的想打人了都--)需求分析那边去百度找了模板.emmmm好多东西感觉听都没听说过QAQ, ...