JQuery Ajax post 参数有时不会在 IE 上发送

IT技术 javascript ajax internet-explorer jquery
2021-02-22 08:50:22

我遇到的问题是,当我使用 jquery ajax post 时,频率非常低(< 2%),post 参数永远不会到达服务器。我确实在访问日志中看到了发布请求。它似乎只发生在 IE 上(我在日志中的 7、8 和 9 上观察到了它)。

当我将呼叫从“post”类型切换到“get”类型时,问题就消失了。

有没有其他人在 IE 上见过这种奇怪的行为?谢谢!

我已经在各种 ajax 调用中看到了这一点,但这是一个典型的调用:

var data= {
    "guess" : "m1",
    "eas" : "hello world"
};

$.ajax({
    url: "http://myco.com/ajaxcall.action",
    data: data,
    type : 'post',
    dataType: 'json',
    success: function(data) {},
    error: function() {}
});

更新:传递“缓存:假”并不能解决问题。

4个回答

上周我一直在跟踪我自己的应用程序中的类似问题(使用 Dojo,而不是 JQuery)。根据您的描述和发生频率,我会说这是同一个问题。

当浏览器和服务器之间使用 HTTP 持久连接时(默认行为),服务器可以随时关闭 HTTP 连接。这会在浏览器开始发送新请求的同时服务器关闭连接时创建一个非常小的计时漏洞。大多数浏览器将使用不同的连接或打开新连接并重新发送请求。这是 RFC 2616 第 8.1.4 节中建议的行为:


客户端、服务器或代理可以随时关闭传输连接。例如,客户端可能在服务器决定关闭“空闲”连接的同时开始发送新请求。从服务器的角度来看,连接是在空闲时关闭的,但从客户端的角度来看,请求正在进行中。

这意味着客户端、服务器和代理必须能够从异步关闭事件中恢复。只要请求序列是幂等的,客户端软件应该重新打开传输连接并重新传输中止的请求序列,而无需用户交互(参见第 9.1.2 节)。


发生这种情况时,Internet Explorer确实会尝试重新发送请求,但是当它恰好是 POST 时,它会通过发送标头(带有 Content-Length)而不是实际数据来破坏它。这是一个格式错误的请求,应该总是导致 HTTP 错误(通常在等待永远不会到来的数据超时之后)。

Microsoft 将此错误记录为 KB 895954(请参阅http://support.microsoft.com/kb/895954)。微软首先在 IE 6 中发现了这个错误。他们提供了一个修补程序,并且从那时起,包括 IE 9 在内的每个版本的 IE 似乎都提供了这个修补程序。这个修复程序有两个问题:

  1. 默认情况下不激活此修补程序。您必须使用 regedit 创建一个非常奇怪的密钥来激活修复程序:HKEY_LOCAL_MACHINE\Software\Microsoft\Internet Explorer\Main\FeatureControl\FEATURE_SKIP_POST_RETRY_ON_INTERNETWRITEFILE_KB895954。

  2. 修复并不能真正解决问题。“固定”行为是当尝试发送请求时连接关闭时,它甚至不会尝试重新发送它。它只是将错误传递给 javascript 应用程序。

看来您必须在代码中添加错误处理程序,并在失败时自己重新发布请求。我正在为我的应用程序寻找这个解决方案。我担心的是,我不确定如何判断我得到的错误是由尝试发送查询失败引起的,还是由于查询而从服务器发回的某些错误(在这种情况下我不知道)想重发)。

我编写了一个 C 程序来模拟 Web 服务器并显式关闭连接以查看浏览器如何处理它。我发现 IE 可以 100% 的时间重现错误行为,而 Firefox、Safari 和 Chrome 可以通过在另一个连接上 100% 的时间正确重新发送 POST 来恢复。也许答案是“不要使用 IE”。

作为对您问题的直接回答:是的,我们刚刚遇到这个问题,找不到合理的解释。它只影响 IE 并且频率非常低 - 花了很长时间才得出结论,它是 IE 中一个零星的 jQuery Ajax 错误。在这种情况下,我们必须通过从服务器返回失败并在 1 秒延迟后重新发布数据来“修复”问题!

像地狱一样的哈克,但似乎是唯一的方法。

肯定没有与 DOM 元素等发生冲突,也没有发生这种情况的合乎逻辑的原因,用户可以多次成功更新页面,但间歇性失败。

应该是bug。

你有没有输入过 jQuery 错误报告?
2021-04-23 08:50:22
不,不要以为我做到了,只是声称胜利并继续前进。我想我不是很喜欢运动:)
2021-05-05 08:50:22

我认为您必须防止在 Internet Explorer 中缓存。尝试将选项缓存设置为 false。

例子:

$.ajax({
    url: "http://myco.com/ajaxcall.action",
    data: data,
    type : 'post',
    dataType: 'json',
    success: function(data) {},
    error: function() {},
    cache: false
});
是的,我同意,我知道这一点,但是 1 年前我在 Internet Explorer 中遇到了缓存问题。我通过速记方法 $.post 发布数据,但从未将其发送到服务器。所以我曾经使用 $.ajax 方法并将选项缓存设置为 false 并且它可以工作。
2021-04-20 08:50:22
对于获取为 true 但帖子不缓存“使用 POST 获取的页面从不缓存,因此 jQuery.ajaxSetup() 中的缓存和 ifModified 选项对这些请求没有影响。”
2021-04-29 08:50:22
我要给缓存标志一个机会......为了科学!
2021-05-07 08:50:22
不幸的是,切换回 post 并将“缓存”标志设置为 false 导致问题再次出现。
2021-05-15 08:50:22

发送到 PHP 的参数是从 IE 中接收的GET

$.ajax ({
     url: "path/to/ajax.php"
    ,method: "POST"
    ,data: {
         var1: "value1"
        ,var2: true
        ,varX: 123123
    }
    ,cache: false
    ,success: function (data) {
        alert (data);
    }
});

然后在 PHP 上你应该使用 REQUEST 而不是 POST:

$var1 = $_REQUEST ["var1"]; // value1
$var2 = $_REQUEST ["var2"]; // true
$var3 = $_REQUEST ["var3"]; // 123123

这个例子可以用它来兼容 IE7