因为我身边很少有人用到GET和POST以外的method,说这些可能没什么意义。

而且不支持部分method的浏览器也只是一部分,不喜欢讨论浏览器兼容性什么的...


但兴许可以从Spring提供的方式里想到别的什么呢。

在此记录处理HTTP method的两个特性。

·Spring form标签

·org.springframework.web.filter.HiddenHttpMethodFilter

其实处理的思路很简单,比如我在页面中写一个


然后我写个filter去获取"真正"的HTTP method。

也许每一次都在一个form下写一个hidden感觉有些多余,于是我可能需要做一个form taglib。

的确,这样高雅了不少,但又多了一份差事。

于是我们可以使用Spring form标签。


引入taglib:

<%@ taglib uri="http://www.springframework.org/tags/form" prefix="sf"%>


然后和html标签没什么区别了,只不过表单的method是delete:


                                                                                                                            


在controller里写一个方法,在@RequestMapping中设置接收的method为delete:

@RequestMapping(value ="/userList",method=RequestMethod.DELETE,headers={"Accept="+MediaType.APPLICATION_JSON_VALUE})
public @ResponseBody User[] queryUserList(){
    System.out.println("delete+++");
    User[] u = new User[4];
    u[0] = new User("0001","King","t;stmdtkg");
    u[1] = new User("0001","King","t;stmdtkg");
    u[2] = new User("0001","King","t;stmdtkg");
    u[3] = new User("0001","King","t;stmdtkg");
    return u;
}


此时访问的话仍然是405,关键还是HiddenHttpMethodFilter。
将HiddenHttpMethodFilter配置与web.xml中:


    httpMethodFilter
    org.springframework.web.filter.HiddenHttpMethodFilter


    httpMethodFilter
    /*


HiddenHttpMethodFilter重写OncePerRequestFilter的doFilterInternal,代码非常简单:

    public static final String DEFAULT_METHOD_PARAM = "_method";
                  
    private String methodParam = DEFAULT_METHOD_PARAM;
                  
@Override
    protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain)
            throws ServletException, IOException {
        String paramValue = request.getParameter(this.methodParam);
        if ("POST".equals(request.getMethod()) && StringUtils.hasLength(paramValue)) {
            String method = paramValue.toUpperCase(Locale.ENGLISH);
            HttpServletRequest wrapper = new HttpMethodRequestWrapper(request, method);
            filterChain.doFilter(wrapper, response);
        }
        else {
            filterChain.doFilter(request, response);
        }
    }


经过这个Filter,到达dispatcherServlet时method就是delete了。