3

我需要确保当有人重新加载或关闭我的页面时,他们的进度会被保存。为了节省进度,我做了一个POSTvia XMLHttpRequest(),将数据发送到服务器。我在一个事件中触发了这个saveData()函数。window.onbeforeunload

问题是,它会进行saveData()一些计算,然后调用 asendData(content)来最终实际发布数据。如果我正在处理和发送的数据很大(> 100kB),则窗口似乎在所有数据都通过服务器之前关闭。(我正在发送一张图片,有时我在另一边只收到一半)

http请求是同步的xhr.open("POST", url, false),但这似乎并没有削减它。

所以我的问题是,如何防止 onbeforeunload 函数终止 UNTIL xhr.readyState == 4?我如何让它等待那个事件?

哦,而且setTimeout()不会工作。窗口将在“时间”到来之前关闭。

这不起作用:

if (!jQuery) {
    setTimeout(attachCode, 100);
    return;
} else {
    // continue and close
}

感谢您的任何见解!

PS:这不应该是“坏习惯”,因为它只需要几秒钟,我不希望用户必须手动保存。此外,在他工作时保存(如在他关闭窗口之前)会减慢应用程序的速度,所以我不能这样做。

[编辑] 作为一种临时措施,如果用户决定留在页面上,我会使用这个技巧来自动保存数据。但是,我真的不想使用任何警报消息。:(

4

2 回答 2

1

不允许浏览器执行正常行为通常是个坏主意。而且由于onbeforeunload您无法暂停卸载,您只能让用户知道他/她正在离开页面,然后让他们决定是否离开页面 - 因此数据未保存。

因此,在您的情况下,我建议您使用自动保存草稿,就像您在 Google 文档中看到的那样 + 当用户离开带有未保存数据的页面时发出警告。

于 2011-02-25T10:28:31.877 回答
1

实际上,您可以在卸载之前减慢浏览器的速度。问题在于JS如何处理ajax请求。

不久前,我不得不对几乎相同的事情进行快速而肮脏的破解——在导航之前记录一些东西。我发现这样做的唯一方法是等待 XHR 请求的返回值。

即使它是同步的,代码的执行也会在后台分叉,实际上并不会阻塞浏览器。您必须获取返回值才能停止脚本上传数据。

请注意,我为此使用了 jQuery,但它适用于本机 JS(我认为.. :))

/* some code above */
var request = {
    async:false,
    cache: false,
    url: this.serviceURL,
    type: 'POST',
    data: {...},
    success: function(data) {}
};
try {
    var asd = $j.ajax(request); // do the request and wait
}
catch (e) {}
/* some code below */

我希望这有帮助。

于 2011-02-25T10:46:22.663 回答