jQuery getJSON不会发送cookie

我在domain1表单domain2上包含JS

 

该脚本没有onload和on按钮单击对domain2的JSONP请求

 $.getJSON( 'http://www.domain2.com/process?callback=?', function(data){ if ( data ) processData( data ); } ); 

然后在domain1上显示数据。

所以这是我的问题:getJSON请求不会将cookie发送到domain2。 最奇怪的是它确实发送了半天cookies而另一半没发送。 🙂

这是请求在不起作用时的样子:

 Request details GET /ajax/embed-user-library?detail=98&callback=jsonp1312398534998 HTTP/1.1 User-Agent: Opera/9.80 (Windows NT 6.1; U; en) Presto/2.9.168 Version/11.50 Host: www.floowie.com Accept: text/html, application/xml;q=0.9, application/xhtml+xml, image/png, image/webp, image/jpeg, image/gif, image/x-xbitmap, */*;q=0.1 Accept-Language: en,sk-SK;q=0.9,sk;q=0.8 Accept-Encoding: gzip, deflate Referer: http://www.sokker.cz/en/test2 Connection: Keep-Alive Response details HTTP/1.1 200 OK Date: Wed, 03 Aug 2011 19:06:51 GMT Server: Apache/2.2.16 (Debian) X-Powered-By: PHP/5.3.5-0.dotdeb.1 Set-Cookie: SESSID=64292b70dc28d7c6c9f13f70070353d8; path=/; domain=.floowie.com Expires: Mon, 26 Jul 1997 05:00:00 GMT Cache-Control: no-cache, must-revalidate Pragma: no-cache Content-Length: 34 Keep-Alive: timeout=15, max=100 Connection: Keep-Alive Content-Type: application/json 

这当它工作时(脚本中没有任何改变):

 Request details GET /ajax/embed-user-library?detail=99&test=1&callback=jsonp1312398534999 HTTP/1.1 User-Agent: Opera/9.80 (Windows NT 6.1; U; en) Presto/2.9.168 Version/11.50 Host: test1.floowie.com Accept: text/html, application/xml;q=0.9, application/xhtml+xml, image/png, image/webp, image/jpeg, image/gif, image/x-xbitmap, */*;q=0.1 Accept-Language: en,sk-SK;q=0.9,sk;q=0.8 Accept-Encoding: gzip, deflate Referer: http://www.sokker.cz/en/test2 Cookie: __utma=254918925.1489796832.1301725317.1312260335.1312298033.44; __utmz=254918925.1312298033.44.11.utmcsr=sokker.cz|utmccn=(referral)|utmcmd=referral|utmcct=/en/test2; lang=en; FLWSESSID=ddd1bc696f83f5a70b5f0f3ae30b4691; __utma=121955676.1030804516.1282595153.1312390656.1312397285.194; __utmb=121955676.8.10.1312397285; __utmc=121955676; __utmz=121955676.1312397285.194.21.utmcsr=floowie.crmserver.cz|utmccn=(referral)|utmcmd=referral|utmcct=/index.php Connection: Keep-Alive Response details HTTP/1.1 200 OK Date: Wed, 03 Aug 2011 19:07:45 GMT Server: Apache/2.2.16 (Debian) X-Powered-By: PHP/5.3.5-0.dotdeb.1 Expires: Mon, 26 Jul 1997 05:00:00 GMT Cache-Control: no-cache, must-revalidate Pragma: no-cache Content-Length: 20 Keep-Alive: timeout=15, max=100 Connection: Keep-Alive Content-Type: application/json 

有人看到这样的行为吗? 它可以解决吗?

谢谢

如果要在不同的域/子域上使用AJAX请求,则必须实现跨源请求。

参考文献:

例子:

您的服务器需要发送此标头:

  • Access-Control-Allow-Origin :test1.floowie.com
  • Access-Control-Allow-Credentials :true //允许cookie /会话凭据
  • 访问控制允许方法 :GET,POST,PUT,DELETE,OPTIONS

您可以全局返回Access-Control-Allow-Origin ,也可以根据您的输入Origin ($ _SERVER [‘HTTP_ORIGIN’])请求标头进行设置。 也适用于Access-Control-Allow-Methods

必须实施OPTIONS请愿书。 在第一次AJAX调用之前,现代浏览器使用OPTIONS方法调用该URL以检索上述标头。

好的,这是第一部分,第二部分是jQuery。 仔细阅读此页面: http : //api.jquery.com/jQuery.ajax/

您需要为每个AJAX调用添加一些选项,您可以在全局范围内执行此操作:

 $(document).ajaxSend(function (event, xhr, settings) { settings.xhrFields = { withCredentials: true }; }); 

或具体:

 $.ajax({ url: a_cross_domain_url, xhrFields: { withCredentials: true } }); 

这个问题让我失去了很多时间……希望它有所帮助。

请注意,如果需要,您无需将Cookie域设置为“.floowie.com”。

您必须使用凭据正确实现CORS请求,以通过Ajax发送和接收cookie。 请参阅developer.mozilla.org ,特别是标题为“凭据请求”的部分。

首先,这是一个带有凭据的简单CORS Ajax请求,使用jQuery 1.5.1+:

 $.ajax({ url: "http://www.domain2.com/process", xhrFields: { withCredentials: true } }).done(function (data) { console.log(data); }); 

请注意xhrFields中的withCredentials标志。 此标志告诉浏览器发送带有外部域请求的cookie,而不是域。 在您的情况下,将发送http://www.domain2.com的 cookie,您将可以访问服务器端的cookie。

在服务器端,您需要向响应添加某些标头:

 Access-Control-Allow-Credentials: true Access-Control-Allow-Origin: www.domain1.com 

重要说明:具有凭据的请求无法将Access-Control-Allow-Origin标头设置为全局( Access-Control-Allow-Origin: * )。 它必须指定域( Access-Control-Allow-Origin: www.domain1.com )。

如果为Access-Control-Allow-Origin标头指定域,则显然会更好。 但是,如果您不知道或不关心CORS请求的Origin ,您可以使用请求中的Origin标头,只需将响应的Access-Control-Allow-Origin标头设置为该标头即可。 在C#中,我们就是这样做的:

 this.Response.AddHeader("Access-Control-Allow-Origin", this.Request.Headers["Origin"]); 

完成所有这些操作后,您设置服务器端的cookie将随响应一起发送回来,浏览器将能够正确处理它们并将它们插入浏览器的http://www.domain2.com cookie存储区。 您发送的任何后续CORS请求也会在请求中发送这些cookie。

如果您发送的请求不是使用GET,POST或HEAD方法,则需要实现预检请求 (请参阅标题为“预检请求”的部分):

与简单请求(如上所述)不同,“预检”请求首先通过OPTIONS方法向另一个域上的资源发送HTTP请求,以便确定实际请求是否可安全发送。 跨站点请求是这样预检的,因为它们可能对用户数据有影响。 特别是,如果出现以下情况,请求会被预检:

  • 它使用GET,HEAD或POST以外的方法。 此外,如果使用POST来发送具有除application / x-www-form-urlencoded,multipart / form-data或text / plain之外的Content-Type的请求数据,例如,如果POST请求将XML有效负载发送到服务器使用application / xml或text / xml,请求预检。

  • 它在请求中设置自定义标头(例如,请求使用诸如X-PINGOTHER之类的标头)

关于IE8和IE9的附注:上面的Ajax调用将在IE8和9中失败。我在我的页面上包含来自MoonScript / jQuery-ajaxTransport-XDomainRequest的JS文件,这自动允许CORS请求在那些旧的IE版本中工作。 但遗憾的是,MS为IE8和9创建的XDomainRequest对象不允许发送或接收cookie。 (有关更多信息,请参阅此MSDN博客文章 )

你有不同的主机。 在第一个例子中,主机是“Host:www.floowie.com”。 第二个是“Host:test1.floowie.com”。

我猜这些cookie最初是由’test1.floowie.com’设置的,你没有指明它们应该可用于’.floowie.com’(即整个域和所有子域)。

你可以发布设置cookie的代码吗?

如果你修复了这个问题,它至少应该表现出一致的行为。 但是,IE可能仍然不会跨子域传递cookie。 这就是我现在正在努力解决的问题,这就是我可以解决你的问题。