2011-12-14 1 views
0

В моих тестах Chrome (и, как я полагаю, как и любой другой браузер веб-браузера), возможно, UNABLE выполняет запрос AJAX ПЕРЕД оставлением страницы.Webkit (Chrome или Safari) делает AJAX безопасным для onunload/onbeforeunload

Представьте, например, что вам нужно очистить что-то на сервере, потому что пользователь нажал на какую-либо ссылку или покинул страницу.

Первое, что я заметил, что window.onunload НЕ работать в любом случае на Chrome

После того, как вы используете window.onbeforeunload убедитесь, что вы не помещайте в организме, как это (Webkit): Потому что это игнорируется. ВЫ ДОЛЖНЫ выполнить window.onbeforeunload = function() {...}, чтобы убедиться, что привязка завершена (или используйте для этого jquery или protoype libs)

В вашем коде 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, кажется, работает так же, как Firefox (Gecko) в данном конкретном случае:

С помощью этого кода вы можете заставить его работать на 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. Это гарантирует, что используется надлежащее событие (onbeforeunload в WebKit и OnUnload на остальных)
  2. Для послало GET Ajax на функцию выгрузить использование ensureAjaxGet(), который будет асинхронный AJAX, когда это возможно и синхронными, когда это необходимо (WebKit)