解决Ajax(常见Put,Delete)请求,出现405(Method Not Allowed)

今天在项目中使用put/delete请求时发现了如下图的错误

失败的解决方法:

在网上查了很多解决方案都没有效果,如添加

还有在Web.config里面webService节点下添加<remove name="WebDAV" /><remove name="WebDAVModule" />等等许多解决方法,最终都以失败告终(ps:我的跨域配置是没有问题的)

发现问题:

经过多次实验发现我的请求中第一次请求的方法是OPTIONS(Request Method:OPTIONS)如下图:

发的是PUT请求,怎么出现了Method为OPTIONS的请求呢?OPTIONS请求是什么呢?在网上查资料后最终明白。

  1. Preflighted Requests(预检请求),PTIONS是浏览器发起的'preflight'请求,征求服务器是否允许该实际请求。
  2. Preflighted Requests是CORS中一种透明服务器验证机制。预检请求首先需要向另外一个域名的资源发送一个 HTTP OPTIONS 请求头,其目的就是为了判断实际发送的请求是否是安全的。

知道了OPTIONS是预检请求了,那么什么条件下浏览器会触发OPTIONS请求?

1、使用了下面任一 HTTP 方法:

  – PUT

  – DELETE

  – CONNECT

  – OPTIONS

  – TRACE

  – PATCH

2、人为设置了对 CORS 安全的首部字段集合之外的其他首部字段。该集合为:

  – Accept

  – Accept-Language

  – Content-Language

  – Content-Type (but note the additional requirements below)

  – DPR

  – Downlink

  – Save-Data

  – Viewport-Width

  – Width

3、 Content-Type 的值不属于下列之一:

  – application/x-www-form-urlencoded

  – multipart/form-data

  – text/plain

那么我们刚好触发了第一个条件:用的put请求。

最终解决:

目前的项目中,不需要考虑的太复杂,简单处理就是放行OPTIONS请求。 (由于时间仓促这里只提供了简单的解决办法,具体的可以自己查下资料)
在普通Filter中先通过request获取到method,然后判断OPTIONS后放行。 

在这里写一些.net Mvc的处理示例,在Global.asax里加上如下处理:

protected void Application_BeginRequest()
        {
            if (Request.Headers.AllKeys.Contains("Origin") && Request.HttpMethod == "OPTIONS")
            {
                Response.End();
            }
        }

最后感谢这篇文章:https://www.aliyun.com/jiaocheng/992452.html和tuy博主http://www.xudihui.com/