我正在尝试在卸载窗口时(即刷新页面时)向数据库发送一些请求。出于某种原因,仅在Safari上,客户端代码被执行,但对服务器的请求永远不会通过。当我在调试器中手动单步执行代码时,服务器确实获得了请求并处理它。
任何人都知道为什么会这样吗?
window.onbeforeunload = function() {
console.log("inside on before unload");
var requestParam = new a.ListRequest();
requestParam.setAction('set_delete');
var callback = function(isSuccess, response) {
if (isSuccess) {
//do something
} else {
// do something else
}
};
// Sends request to server
a.Fetch.list(requestParam, callback);
}
答案 0 :(得分:5)
可能在Fetch调用中发生的请求是异步的,Safari不会等到它完成,然后再转到下一页/关闭选项卡。如果你可以使呼叫同步,它应该工作。请记住,在某些工具中通常不鼓励和弃用同步调用。
与Jquery相关的答案对同步调用有一个很好的解释:https://stackoverflow.com/a/11755262/1341437
答案 1 :(得分:2)
您可以使用Beacon API
(FF,Chrome,Opera):
window.addEventListener('unload', logData, false);
function logData() {
navigator.sendBeacon("/log", analyticsData);
}
用户代理通常会忽略在卸载处理程序中生成的异步XMLHttpRequests
。要解决此问题,分析和诊断代码通常会在XMLHttpRequest
或unload
处理程序中生成同步beforeunload
以提交数据。同步XMLHttpRequest
强制用户代理延迟卸载文档,并使下一个导航看起来更慢。下一页无法避免这种对页面加载性能不佳的看法。
使用sendBeacon()
方法,当用户代理有机会这样做时,数据将异步传输到Web服务器,而不会延迟卸载或影响下一个导航的性能。
答案 2 :(得分:0)
您可以通过将async属性设置为false async:false
window.onbeforeunload = function() {
$.ajax({
// Query to server
async:false,
method: "GET",
url: "your.page",
data: { param1 : "value1" }
}).done(function(jqXHR, textStatus) {
// Verify good data
// Do stuff
alert( "Request done: " + textStatus );
}).fail(function( jqXHR, textStatus ) {
alert( "Request failed: " + textStatus );
});
}
答案 3 :(得分:0)
正如@craigts所说,在返回ajax调用之前浏览器已经消失。 你可能会在那个页面上再多几秒钟。
window.onbeforeunload = function(e) {
return 'Dialog text here.';
};
但是,您的用户会觉得这很烦人。
第二个选项,找到另一个事件而不是等待页面卸载。持续捕获数据。捕捉它改变。用户是否会使用链接继续?如果是这样,你可以用cancelEvent()劫持链接,然后在ajax返回后继续。