处理CORS preflight请求ASP.NET MVC行动 [英] Handling CORS Preflight requests to ASP.NET MVC actions
问题描述
我试图执行一个跨域POST请求到ASP.NET MVC控制器动作。该控制器操作接受和放大器;使用的各种参数。的问题是,preflight请求发生时,控制器采取行动实际上试图执行与放大器;因为OPTIONS请求没有通过任何数据,控制器动作抛出一个500 HTTP错误。如果我删除code使用参数,或参数本身,整个请求链成功完成。
I'm trying to perform a cross-domain POST request to an ASP.NET MVC controller action. This controller action accepts & uses various parameters. The problem is that when the preflight request happens, the controller action actually attempts to execute & because the OPTIONS request doesn't pass any data, the controller action throws out a 500 HTTP error. If I remove the code that uses the parameter, or the parameter itself, the entire request chain is completed successfully.
这是如何实现的一个例子:
An example of how this is implemented:
控制器动作
public ActionResult GetData(string data)
{
return new JsonResult
{
Data = data.ToUpper(),
JsonRequestBehavior = JsonRequestBehavior.AllowGet
};
}
客户端code
<script type="text/javascript">
$(function () {
$("#button-request").click(function () {
var ajaxConfig = {
dataType: "json",
url: "http://localhost:8100/host/getdata",
contentType: 'application/json',
data: JSON.stringify({ data: "A string of data" }),
type: "POST",
success: function (result) {
alert(result);
},
error: function (jqXHR, textStatus, errorThrown) {
alert('Error: Status: ' + textStatus + ', Message: ' + errorThrown);
}
};
$.ajax(ajaxConfig);
});
});
</script>
现在,只要preflight请求发生,它会返回一个HTTP 500 code,因为数据参数为空,看到OPTIONS请求不传递任何值。
Now, whenever the preflight request happens, it returns a 500 HTTP code, because the "data" parameter is null, seeing as the OPTIONS request doesn't pass any values.
服务器应用程序已经设置在我的本地IIS在端口8100和放大器;运行客户端code中的页面设置端口8200来模拟跨域调用。
The server application has been set up in my local IIS on port 8100 & the page running the client-side code is set up on port 8200 to mimic the cross-domain calls.
我也用下面的头配置的机子上(8100):
I have also configured the host (on 8100) with the following headers:
Access-Control-Allow-Headers: Content-Type
Access-Control-Allow-Methods: POST, GET
Access-Control-Allow-Origin: http://localhost:8200
一个解决办法我已经找到了,是要检查执行的动作和放HTTP方法;如果它是一个OPTIONS请求,只是返回空白的内容,否则执行的操作code。像这样:
One workaround I had found, was to check the HTTP method that executes the action & if it's a OPTIONS request to just return blank content, otherwise execute the action code. Like so:
public ActionResult GetData(string data)
{
if (Request.HttpMethod == "OPTIONS") {
return new ContentResult();
} else {
return new JsonResult
{
Data = data.ToUpper(),
JsonRequestBehavior = JsonRequestBehavior.AllowGet
};
}
}
但这种方法感觉很笨重给我。我认为将这种逻辑到属性
,但即使这意味着每一个装饰,将让使用CORS它称为动作。
But this approach feels very clunky to me. I considered adding this sort of logic to an Attribute
, but even this would mean decorating every action that will get called using CORS with it.
有没有更优雅的解决方案,以获得此功能工作?
Is there a more elegant solution to getting this functionality to work?
推荐答案
所以,我发现,有效的解决方案。对于每个请求,我检查它是否是一个CORS请求&安培;请求是否即将与OPTIONS动词,这表明它是preflight请求。如果是,我只是发送一个空的响应回(只包含当然IIS中配置的头),从而否定控制器动作执行。
So I have found a solution that works. For each request, I check whether it's a CORS request & whether the request is coming in with the OPTIONS verb, indicating that it's the preflight request. If it is, I just send an empty response back (which only contains the headers configured in IIS of course), thus negating the controller action execution.
然后,如果客户确认它允许执行基于从preflight返回标头的要求,实际的POST进行&放大器;控制器的执行动作。和示例我code的:
Then if the client confirms it's allowed to perform the request based on the returned headers from preflight, the actual POST is performed & the controller action is executed. And example of my code:
protected void Application_BeginRequest()
{
if (Request.Headers.AllKeys.Contains("Origin") && Request.HttpMethod == "OPTIONS") {
Response.Flush();
}
}
如前所述,这为我工作,但如果有谁知道一个更好的方式,或在我目前的执行任何瑕疵的,我会AP preciate听到他们。
As mentioned, this worked for me, but if anyone knows of a better way, or of any flaws in my current implementation, I would appreciate to hear about them.
这篇关于处理CORS preflight请求ASP.NET MVC行动的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!