使用jQuery/Ajax从JavaScript调用WCF/JSON/REST WebService

pet*_*ski 9 authentication rest wcf jquery json

我知道有很多关于此的问题 - 相信我,我已经阅读了很多这些问题并尝试了解答.

(此项目适用于内部公司局域网,而非互联网)

我们有一个WCF Web服务,它是RESTFUL并发送/接收JSON,它需要NTLM(Curb也会很好)auth /凭证以确保主叫用户(来自浏览器是他们所说的人),这是在浏览器/客户端和WCF绑定的服务:

 <bindings>
  <webHttpBinding>
    <binding name="webHttpBindingAuth">
      <security mode="TransportCredentialOnly">
        <transport clientCredentialType="Ntlm"/>
      </security>
    </binding>
  </webHttpBinding>
</bindings>
Run Code Online (Sandbox Code Playgroud)

使用Fiddler,我可以成功调用服务GET和POST上的方法,并提供了我调整我们发送给Web服务的JSON(例如包含会话ID),它很快就会顺利进行.

当我们尝试使用JavaScript/jQuery来调用web服务时,问题就出现了; 我们的想法是Web服务器将HTML/JS提供给客户端浏览器,然后浏览器应该调用WCF Web服务来获取会话并允许用户执行一些操作(我们总共有3个方法).

首先,我们遇到了X-Domain问题,我们试图通过让Web服务器返回正确的头文件来解决这个问题(Access-Control-Allow-Origin).这并没有阻止像SRIron这样的浏览器告诉我们;

XMLHttpRequest cannot load http://{webServiceUri}/InstantMessagingService/chat/start/{username}. Origin http://{web**Server**Uri} is not allowed by Access-Control-Allow-Origin.
Run Code Online (Sandbox Code Playgroud)

在此之后,我调查了使用Silverlight的可能性(似乎不支持NTLM auth over WebHttpBinding),反向代理已经出来,因为在dev中使用的IIS服务器将不会用于prod(我相信它是WebSphere,但不在我们的控制之下); 接下来我看了看这个:

http://msmvps.com/blogs/paulomorgado/archive/2007/04/27/wcf-building-an-http-user-agent-message-inspector.aspx

这让我觉得WCF Web服务实际上是需要告诉浏览器允许调用它的东西(如果这是有道理的).实现了示例中的所有代码之后,我发现从未调用过ApplyClientBehavior来尝试将标头返回给客户端(也在Fiddler中监控它).更多谷歌搜索引导我:

http://social.msdn.microsoft.com/Forums/en-US/wcf/thread/707aa031-f4ff-47ab-ba5b-730f7930605e/

由于我们使用jQuery而不是某些.NET客户端/服务引用/代理/应用程序访问Web服务,所以我认为不可能预先请求发送这些标头以允许访问服务.此外,Fiddler似乎认为它正在尝试调用http://../chat/start/ ..方法时获得401 Unauthorized .

这是我用来尝试进行调用的jQuery(我提供了一些设置,希望它能够正常工作):

var url = webserviceUrl + "chat/start/" + remoteUserUri;

$.ajax({
    type: 'GET',   
    url: url,
    crossDomain: true,
    beforeSend: function(xhr){ xhr.withCredentials = true; },
    contentType: "application/json; charset=utf-8",               
    success: function (data) { conversationStarted(data); },
    dataType: 'json'
}); 
Run Code Online (Sandbox Code Playgroud)

好的,如果有人有有用的提示或想法,请开火.我会回复和编辑等,以确保它保持最新,我希望我没有错过任何东西(但我的头从我的谷歌搜索旋转一点).

此外,我知道可能有更好的方法来做到这一点,但我想以最清洁/最快的方式从现在开始 - 即没有很多代码更改,重写等我也可以发布如果人们认为它们确实有用,那就是配置.

pet*_*ski 3

最后我不得不解决这个问题,我们让负责 Web 服务器的人同意提供一个 IFrame,它指向我们的 IIS 托管页面(包含 JS 等的页面)

然后,利用 WCF/Windows 的魔力,我们在端口 80 上托管 WCF 服务,从而绕过 X-Domain 原始内容。这样我就可以使用 REST/JSON,而不必使用 JSONP。

我知道根据我指定的标准,这不是问题的答案,但我认为我最终完全没有选择。