jquery abort的bug,ie请求长轮询的bug
最近公司项目需要,做了一些web im的研究,在demo测试的过程中发现了以下3个问题:
1、请求不间断的长轮询,在IE下页面刷新的时候,会卡死
2、初步估计是ie请求数受限,于是在页面卸载前对请求进行abort()处理,却发现在报错了,显示对象不支持该方法。
3、ff和chrome在刷新页面的时候会自动中断请求,并执行success回调
针对第二个问题,查了些资料,总结是jquery abort方法在ie7下的bug,解决方法如下:
打开jquery源文件,找到以下代码
1. try {
2. var oldAbort = xhr.abort;
3. xhr.abort = function () {
4. if (xhr) {
5. oldAbort.call(xhr);
6. }
7. onreadystatechange("abort");
8. };
9. } catch (e) { }
替换成
1. try {
2. var oldAbort = xhr.abort;
3. xhr.abort = function () {
4. if (xhr) {
5. if (oldAbort.call === undefined) {
6. oldAbort();
7. } else {
8. oldAbort.call(xhr);
9. }
10. }
11.
12. onreadystatechange("abort");
13. };
14. } catch (e) { }
OK,jquery abort的bug解决了!
这个BUG解决了,发布上去测试,问题依然存在!还是卡死!
请求是这样写的
1. function queryMsg() {
2. ajaxquery = $.ajax({
3. type: "get",
4. url: "http://192.168.94.26/feed/subscribe",
5. cache: false,
6. success: function (data, textStatus) {
7. if (data) {
8. //处理结果
9. }
10. queryMsg();//继续新的请求
11. }
12. });
13. }
解决方法:
将queryMsg()替换成setTimeout(queryMsg,0)
OK,解决了!
以上两个操作缺一不可。
另外,ff 和 chrome 下在页面unload的时候对于没有请求完成的长连接,会强制转到success状态,也就是说刷新页面的时候会触发ajax中的success事件,ie加了abort() 以后也会出现同样问题,所以针对这个问题还需要做特殊处理,我的做法是加个开关参数,通过onbeforeunload事件对开关参数赋值。
完整代码:
1. //开关
2. var _flag_is_unload = false;
3. //请求变量
4. var ajaxquery = null;
5. //查询消息
6. function queryMsg() {
7. ajaxquery = $.ajax({
8. type: "get",
9. url: "http://192.168.94.26/feed/subscribe",
10. cache: false,
11. success: function (data, textStatus) {
12. if(!_flag_is_unload){
13. if (data) {
14. //处理消息
15. }
16. setTimeout(queryMsg, 0);
17. }
18. }
19. });
20.
21. }
22. function funBeforeunload() {
23. //中止请求
24. ajaxquery.abort();
25. //开关状态
26. _flag_is_unload = true;
27. }
总结:
1、在页面unload时候 ff/chrome会自动结束未完成的ajax请求,而ie不会,需要手动abort()
2、jquery(我测试的版本1.4.2) abort()方法存在bug,需要进行修复
3、由于abort()也会触发jquery ajax 的success回调,所以需要对其做特殊处理
摘自 JsLover