WCF REST 服务模板 40(CS) 跨域错误
Posted
技术标签:
【中文标题】WCF REST 服务模板 40(CS) 跨域错误【英文标题】:WCF REST Service Template 40(CS) Cross domain error 【发布时间】:2014-11-11 10:22:43 【问题描述】:您好,我有一个 WCF Rest 服务,使用的是(WCF REST 服务模板 40(CS))。我设法让它返回 Json 响应。项目运行时工作正常。但是当我尝试从浏览器对服务进行 Ajaxcall 时,出现错误:
跨域请求被阻止:同源策略不允许读取
http://192.168.0.70:8001/Service/test
的远程资源。 这可以通过将资源移动到同一域或 启用 CORS。
还有 Ajax 调用:
$.ajax(
type: "POST",
url: "http://192.168.0.70:8001/Service/test",
contentType: "application/json; charset=utf-8",
dataType: "json",
async: true,
cache: false,
success: function (msg)
var Tabels = msg.d;
alert('success');
);
这是 web.config:
<?xml version="1.0"?>
<configuration>
<connectionStrings>
<add name="ConString" connectionString="SERVER=localhost;DATABASE=fabapp;UID=root;PASSWORD=;"/>
</connectionStrings>
<system.web>
<compilation debug="true" targetFramework="4.0" />
</system.web>
<system.webServer>
<httpProtocol>
<customHeaders>
<add name="Access-Control-Allow-Origin" value="*" />
</customHeaders>
</httpProtocol>
<modules runAllManagedModulesForAllRequests="true">
<add name="UrlRoutingModule" type="System.Web.Routing.UrlRoutingModule, System.Web, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a" />
</modules>
</system.webServer>
<system.serviceModel>
<serviceHostingEnvironment aspNetCompatibilityEnabled="true"/>
<standardEndpoints>
<webHttpEndpoint>
<!--
Configure the WCF REST service base address via the global.asax.cs file and the default endpoint
via the attributes on the <standardEndpoint> element below
-->
<standardEndpoint name="" helpEnabled="true" automaticFormatSelectionEnabled="false" defaultOutgoingResponseFormat="Json"/>
</webHttpEndpoint>
</standardEndpoints>
</system.serviceModel>
</configuration>
我尝试添加 crossDomainScriptAccessEnabled="true" 但是当我这样做时,该服务也无法在本地主机上运行。我明白了:
认证不支持跨域javascript回调 服务。
我需要在 web.config 文件中更改什么?
【问题讨论】:
你试过我的解决方案了吗? 【参考方案1】:实际上,我曾经遇到过这个问题,我进一步检查了 WebAPI,并且在分析时需要同样的努力。所以我不得不修复这个CORS with WCF
。我将尝试简短地解释一下。开始了。当您使用 CrossOrigin 访问 WCF 请求时,例如从存在于不同域中的 JS 代码和从 JS ,您尝试执行 PUT
或 POST
请求,第一个浏览器发送 OPTION
请求 405 HTTP Status
,看看是否这样域在允许列表中,那么如果您的WCF
响应OPTIONS
请求,发送带有标头值的所需响应,那么浏览器将再次执行POST
或PUT
请求(以前的浏览器发出),它将按预期工作。
注意:您不能发送("Access-Control-Allow-Origin", "*")
,因为有一项安全功能,要求将所需的域名列在Access-Control-Allow-Origin
而不是*
。
更多信息-
http://social.msdn.microsoft.com/Forums/ro-RO/5613de55-2573-49ca-a389-abacb39e4f8c/wcf-rest-service-post-cross-domain-not-working?forum=wcf
https://***.com/questions/26163802/wcf-cors-request-from-jquery-not-working
根据实际经验,我在该标题中尝试了*
,但它不起作用。如果你不相信我,那就去试试吧。
最后代码如下。你需要把它放在Global.asax
。
protected void Application_BeginRequest(object sender, EventArgs e)
String domainname = HttpContext.Current.Request.Headers["Origin"].ToString();
if (IsAllowedDomain(domainname))
HttpContext.Current.Response.AddHeader("Access-Control-Allow-Origin", domainname);
String allowedmethods = "POST, PUT, DELETE, GET";
String headers = HttpContext.Current.Request.Headers["Access-Control-Request-Headers"].ToString();
String accesscontrolmaxage = "1728000";
String contenttypeforoptionsrequest = "application/json";
if (HttpContext.Current.Request.HttpMethod == "OPTIONS")
//These headers are handling the "pre-flight" OPTIONS call sent by the browser
HttpContext.Current.Response.AddHeader("Access-Control-Allow-Methods", allowedmethods);
HttpContext.Current.Response.AddHeader("Access-Control-Allow-Headers", headers);
HttpContext.Current.Response.AddHeader("Access-Control-Max-Age", accesscontrolmaxage);
HttpContext.Current.Response.AddHeader("ContentType", contenttypeforoptionsrequest);
HttpContext.Current.Response.End();
private bool IsAllowedDomain(String Domain)
if (string.IsNullOrEmpty(Domain)) return false;
string[] alloweddomains = "http://192.168.0.70:8001"; // you can place comma separated domains here.
foreach (string alloweddomain in alloweddomains)
if (Domain.ToLower() == alloweddomain.ToLower())
return true;
return false;
【讨论】:
* 正在工作,由于某种原因,您只是遇到了一些问题(可能是因为localhost
域)。这个答案是你的还是你引用了@Samir 的另一个答案?他的回答早了 2 小时,而你的回答似乎是他加上一些 cmets 的复制粘贴。
@WiktorZychla,是的,我的解决方案有效,我的意思是我在 6 个月前就使用过这个,而问题是 HttpContext.Current.Response.AddHeader("Access-Control-Allow-Origin", "*");
不适用于我,所以我继续解决这个问题,这将发送带有所需域的标头,而不是 *
。
@ArindamNayak Ur 解决方案不起作用。我在这一行收到错误Object reference not set to an instance of an object.
:String domainname = HttpContext.Current.Request.Headers["Origin"].ToString();
我明白了,你应该不会出错,尝试一下使用domainname
= "http://192.168.0.70:8001/"
,看看是否有帮助
谢谢,看起来它正在工作。我会更多地测试它并让你知道【参考方案2】:
将以下内容放入您的 wcf 应用程序的 global.asax 文件中
protected void Application_BeginRequest(object sender, EventArgs e)
HttpContext.Current.Response.AddHeader("Access-Control-Allow-Origin", "*");
if (HttpContext.Current.Request.HttpMethod == "OPTIONS")
HttpContext.Current.Response.AddHeader("Cache-Control", "no-cache");
HttpContext.Current.Response.AddHeader("Access-Control-Allow-Methods", "GET, POST");
HttpContext.Current.Response.AddHeader("Access-Control-Allow-Headers", "Content-Type, Accept");
HttpContext.Current.Response.AddHeader("Access-Control-Max-Age", "1728000");
HttpContext.Current.Response.End();
【讨论】:
我已经尝试过您提供的解决方案,但它不适合我。【参考方案3】:您可能想查看此链接中的帖子:
http://www.codeproject.com/Articles/223572/Calling-Cross-Domain-WCF-service-using-Jquery-Java
Ajax 允许在后台获取数据而不干扰 展示。通过使用 XMLHttpRequest 对象完成的 Ajax 调用允许 用于建立 HTTP 连接的客户端 JavaScript 代码。但是阿贾克斯打电话 由于限制,不允许跨域获取数据 由浏览器强加。请求时发出安全错误 来自另一个域的数据。避免安全错误的一种方法是 控制数据所在的远程服务器,每个请求都发送到 同一个域。这就引出了一个问题,如果数据有什么好玩的 仅来自自己的服务器?如果需要从中获取数据怎么办 另一台服务器?
有一种方法可以摆脱这种限制 - 插入 网页中的动态脚本元素,其来源为指向 到另一个域中的服务 URL 并获取脚本中的数据 本身。当脚本加载时,它会执行。它之所以有效,是因为 同源策略不会阻止动态脚本插入和 将脚本视为从域加载 提供了网页。但是如果这个脚本试图加载一个文档 从另一个域,它将失败。幸运的是,您可以改进 这种技术是通过将 JavaScript Object Notation (JSON) 添加到组合中来实现的。
JSONP 或“带填充的 JSON”是对基本 JSON 数据的补充 格式,一种使用模式,允许页面从 服务器在不同的域。为了解决这个问题,JSONP 是 一种称为跨域资源的更新方法的替代方法 分享。
在同源策略下,提供的网页来自 server1.example.com 无法正常连接或通信 server1.example.com 以外的服务器。一个例外是 html 元素。充分利用开放政策 元素,一些页面使用它们来检索 JavaScript 代码 对其他动态生成的 JSON 格式数据进行操作 起源。这种使用模式称为 JSONP。 JSONP 请求 检索的不是 JSON,而是任意 JavaScript 代码。他们被评估 由 JavaScript 解释器解析,而不是由 JSON 解析器解析。
就我个人而言,我之前也遇到过这个问题,但后来我所做的是我改变了架构。我通常只会从我的 Web 服务器调用 WCF。所以
来自浏览器的 AJAX 请求 -> Web 服务器 -> WCF 服务
我认为出于安全目的,此限制旨在防止许多安全漏洞。但是,如果您真的想实现您想要的并且之前的答案不符合您的要求,您可能需要查看这篇文章作为替代方案。看起来很有希望。请让我更新。
希望对您有所帮助。谢谢。
【讨论】:
以上是关于WCF REST 服务模板 40(CS) 跨域错误的主要内容,如果未能解决你的问题,请参考以下文章
跨域 jQuery Ajax 请求和 WCF REST 服务