这是我的问题:当我打开一个页面时,它会触发一系列的ajax调用。如果我然后按Shift + Refresh,所有这些ajax调用都被视为错误,并在整个页面本身重新加载之前显示其错误消息对话框。
所以错误是由客户端触发的 - 无论如何我可以找出是否是这种情况所以我可以忽略它?例如在xmlhttprequest中,或在ajax函数中(我正在使用jquery btw)
答案 0 :(得分:37)
有几种建议的检测方法:
有几个人建议使用beforeunload
处理程序来设置布尔标志,以便错误处理程序可以知道页面正在卸载(请参阅下面的相关/重复帖子列表)。除了mobile Safari on iOS doesn't support the beforeunload
event。
Sachindra suggested这种方法不是立即触发错误函数,而是在setTimeout(..., 1000)
中延迟了一秒。这样,在调用错误处理程序时,页面很可能实际上已消失。 “好机会”就是这样。我打赌如果我有一个巨大的页面,例如许多<input>
s,卸载可能需要1秒多的时间,然后错误处理程序可能会解雇。
因此,我建议reliably detecting beforeunload
support的组合,如果不支持beforeunload
(咳嗽 iPad / iPhone 咳嗽),请回复Sachindra的延迟技巧
查看beforeunload
检测的完整解决方案以及此jsfiddle中的所有内容。
看起来情况是a little better for jQuery 2.x than for 1.x,但2.x似乎也有点不稳定,所以我仍然认为这个建议是谨慎的。
P.S:还有一些建议涉及测试XHR
/ jqXHR
对象中的某些字段。 (Here和here)。在长时间运行的AJAX调用期间,我还没有能够区分用户导航和重新启动Web服务器的组合,因此我没有发现这种方法对我有用。
这也是对这些相关/重复的Stack Overflow问题的回答:
以及Stack Overflow之外的这些帖子:
答案 1 :(得分:19)
[这是上一个答案的编辑,其中包含我已经解决的突出问题]
当用户通过刷新,单击链接或更改浏览器中的URL导航离开页面时,jQuery会抛出错误事件。您可以通过为ajax调用实现错误处理程序并检查xmlHttpRequest对象来检测这些类型的错误:
$.ajax({
/* ajax options omitted */
error: function (xmlHttpRequest, textStatus, errorThrown) {
if(xmlHttpRequest.readyState == 0 || xmlHttpRequest.status == 0)
return; // it's not really an error
else
// Do normal error handling
});
答案 2 :(得分:6)
var isPageBeingRefreshed = false;
window.onbeforeunload = function() {
isPageBeingRefreshed = true;
};
$.ajax({
error: function (xhr, type, errorThrown) {
if (!xhr.getAllResponseHeaders()) {
xhr.abort();
if (isPageBeingRefreshed) {
return; // not an error
}
}
}
});
答案 3 :(得分:2)
上述技术不适用于定期刷新页面(例如每半秒)。我已经发现,通过将错误处理过程延迟一小段时间,可以避免刷新页面引起的错误。
示例:
$.ajax(...)
.success(...)
.error(function(jqXHR) {
setTimeout(function() {
// error showing process
}, 1000);
});
除此之外
window.onbeforeunload = function(){//停止ajax调用}
事件可用于不太频繁刷新ajax调用。
答案 4 :(得分:2)
nisanth074 和 PeterV.Mørch的组合版本,对我有用。
示例:强>
var isPageBeingRefreshed = false;
$(window).on('beforeunload', function(){
isPageBeingRefreshed = true;
});
$.ajax({
// Standart AJAX settings
}).error(function(){
if (!isPageBeingRefreshed) {
// Displaying error message
}
});