jQuery ajaxerror () manipulador de fogo se o usuário sair da página antes do fim da página carregar
Pergunta
Usamos o manipulador global de Ajaxerror () da JQuery para alertar o usuário de quaisquer falhas do Ajax:
$(document).ajaxError(function() {
$("There was a network or server error. Please try again later.").dialog({
title: "Error",
modal: true,
resizable: false,
buttons: { 'Ok': function() { (this).dialog("close"); } }
});
});
Infelizmente, esse manipulador de erros global também dispara se o usuário deixar a página antes de terminar o carregamento. Aqui estão as etapas para reproduzir o erro:
- Visitas ao usuário A página A, que inclui elementos que carregam via AJAX.
- Ajax Elementos na página A Begining carregando.
- O usuário clique no link para visitar a página B antes da Elementos Ajax na página A terminou o carregamento.
- A caixa de diálogo de erro aparece brevemente antes do redirecionamento do navegador para a página B.
Alguma idéia de como podemos fazer com que o ajaxerror () não acione quando o erro é causado diretamente pelo usuário que visita uma nova página?
ATUALIZAÇÃO: Aqui está o meu código agora, depois de incorporar as sugestões nos comentários:
// I added a 3 second delay to our error dialog, enough time
// for the user to leave for a new page:
$(document).ajaxError(function() {
setTimeout(my_error_handler, 3000);
});
// Warn user before leaving page if AJAX is still loading.
// Not sure I'll keep this:
$(document).ajaxStart(function() {
ajaxing = true;
});
$(document).ajaxStop(function() {
ajaxing = false;
});
window.onbeforeunload = function() {
if (typeof(ajaxing) != 'undefined' && ajaxing) {
return "Page elements are still loading!";
}
};
Solução
Bem, sim, se o usuário navegar para outra página, o XHR abortará, o que é, na verdade, uma comunicação malsucedida. Uma solução seria registrar um ouvinte para o onbeforeunload
evento, e desbloquear ajaxError
Lá, basicamente dizendo: o usuário está prestes a sair da página, então não desejo ser informado dos erros do AJAX que podem seguir.
Alguns sites, porém, como o Gmail, fazem o contrário: se você tentar navegar para longe da página enquanto ainda houver alguns pedidos de Ajax pendentes, isso fornece um rápido que diz que você tem alguns processos em execução e vamos O usuário decide se deve permanecer no site até que a solicitação termine ou siga em frente e navegue.
Outras dicas
Com base na resposta de David Hedlund acima, aqui está o código que funciona para mim:
//enable global ajax error handling
$(document).ajaxError(function (event, request, settings) {
//your error handling code here
});
//user leaving page so ignore any unfinished ajax loads
$(window).bind('beforeunload', function () {
$(document).unbind('ajaxError');
});
Eu tenho o 'ajaxError'
especifica da seção de comentários de JQuery Ajaxerror Documentação. Eu tive que amarrar beforeunload
para $(window)
Para apoiar o Chrome (ou seja, estava funcionando bem com o documento). .ajaxError
não disparou quando eu estava vinculando para $(window)
É por isso que tenho essa solução de janela/documento.