2011-12-14 73 views
0

在我的測試中,Chrome瀏覽器(以及其他任何可能的webkit瀏覽器)無法在離開頁面之前執行AJAX請求。在onunload/onbeforeunload上安全地執行AJAX的Webkit(Chrome或Safari)方式

想象一下,例如,您需要清理服務器上的某些內容,因爲用戶點擊了某個鏈接或離開了該頁面。

我注意到的第一件事是,window.onunload DOES NOT總之在Chrome一旦您使用window.onbeforeunload確保你不要放在身體像這樣的工作

(Webkit的?):因爲這被忽略。你必須做window.onbeforeunload = function(){...}以確保綁定完成(或使用jQuery或原型類型的庫)

在你的onbeforeunload代碼中,像這樣的ASYNCHRONOUS Ajax不起作用或者:

var req = new XMLHttpRequest(); 
req.open("GET", "dosomething.page"); 
req.send(null); 

(雖然這會工作在Firefox)

如果只是如果提出要求同步這樣它將工作:

var req = new XMLHttpRequest(); 
req.open("GET", "dosomething.page",false); 
req.send(null); 

雖然請記住,如果服務器沒有回覆,同步會導致瀏覽器掛起2分鐘。

另外,Firefox似乎不適用於onunload。

因此,最後,您必須爲每個瀏覽器或瀏覽器系列提供不同的代碼路徑。

我還沒有能夠正確地測試IE瀏覽器。 有誰知道? IE更像是Chrome還是FF? 還是它不同?

回答

0

IE瀏覽器似乎在這種特殊情況下的工作就像火狐(壁虎):

有了這個代碼,你可以把它的WebKit的工作,Firefox和IE:

// Browser detection 
var Browser={ 
    IE:  !!(window.attachEvent && !window.opera), 
    Opera: !!window.opera, 
    WebKit: navigator.userAgent.indexOf('AppleWebKit/') > -1, 
    Gecko: navigator.userAgent.indexOf('Gecko') > -1 && navigator.userAgent.indexOf('KHTML') == -1, 
    MobileSafari: !!navigator.userAgent.match(/Apple.*Mobile.*Safari/) 
}; 

// Ensures the Ajax Get is performed... Asynchronously if possible 
// or Synchronously in WebKit Browsers (otherwise it'll most probably fail) 
function ensureAJAXGet(url, args) { 
    var async=!Browser.WebKit; 
    var finalUrl=url; 
    var sep=""; 
    for (var key in args) { 
     sep=(sep=="?")?"&":"?"; 
    finalUrl=finalUrl+sep+encodeURIComponent(key)+"="+encodeURIComponent(args[key]); 
    } 
    var req = new XMLHttpRequest(); 
    req.open("GET", finalUrl,async); 
    req.send(); 
    return req; 
} 

// Sets up an unload function for all browsers to work (onunload or onbeforeunload) 
function onUnload(func) { 
    if(Browser.WebKit) { 
     window.onbeforeunload=func;  
    } else { 
     window.onunload=func; 
    } 
} 

HTML測試可能是這樣的:

var browser="?" 
if (Browser.IE) { 
    browser="IE"; 
} else if (Browser.Opera) { 
    browser="Opera"; 
} else if (Browser.WebKit) { 
    browser="WebKit"; 
} else if (Browser.Gecko) { 
    browser="Gecko"; 
} else if (Browser.MobileSafari) { 
    browser="MobileSafari"; 
} 

function unload() { 
    ensureAJAXGet("testajax.jsp", {"browser": browser}); 
} 

onUnload(function() { unload(); }); 

即:

  1. 要做一些onunload,請調用onUnload()而不是直接使用window.onload或window.onunload。這確保使用正確的事件(在WebKit中onbeforeunload並在其他onunload上)
  2. 若要在卸載函數上發送一些GET Ajax,請使用ensureAjaxGet(),如果可能,它將是異步AJAX,並在需要時同步(WebKit)
相關問題