JQuery Ajax - Ajax çağrısı yaparken Ağ Bağlantısı hatası nasıl tespit edilir


91

Her 5 dakikada bir sunucuya Ajax çağrısı yapan bazı Javascript JQuery kodum var, bu sunucu oturumunu canlı tutmak ve kullanıcının oturum $.ajax()açmasını sağlamak için. JQuery'de yöntemi kullanıyorum . Bu işlev, kullanıcının internet bağlantısının KeepAlive komut dosyasının çalışmaya devam etmesi için kesilmesi durumunda kullanmaya çalıştığım bir 'error' özelliğine sahip görünüyor. Aşağıdaki kodu kullanıyorum:

var keepAliveTimeout = 1000 * 10;

function keepSessionAlive()
{
    $.ajax(
    {
        type: 'GET',
        url: 'http://www.mywebapp.com/keepAlive',
        success: function(data)
        {
            alert('Success');

            setTimeout(function()
            {
                keepSessionAlive();
            }, keepAliveTimeout);
        },
        error: function(XMLHttpRequest, textStatus, errorThrown)
        {
            alert('Failure');

            setTimeout(function()
            {
                keepSessionAlive();
            }, keepAliveTimeout);
        }
    });
}

Çalıştırdığımda, her 10 saniyede bir uyarı kutusunda ekranda 'Başarılı' açılır penceresini alacağım, bu da sorun değil. Ancak, ağ kablosunu çıkarır çıkarmaz hiçbir şey alamıyorum, hata işlevinin çağrılmasını ve bir 'Arıza' uyarı kutusu görmesini bekliyordum, ancak hiçbir şey olmuyor.

"Hata" işlevinin yalnızca sunucudan döndürülen "200" olmayan durum kodları için olduğunu varsaymakta haklı mıyım? Ajax araması yaparken ağ bağlantısı sorunlarını tespit etmenin bir yolu var mı?


İstemcinin ağ kablosunu veya sunucunun ağ kablosunu çıkardınız mı?
Jeff Sternal

Bağlantınızı çıkardıktan sonra 'başarılı' uyarısı almaya devam ediyor musunuz?
Wilkins

3
@Jeff - Soruna neden olan istemci tarafındaki internet bağlantısı kaybı. İnanılmaz bir şekilde, bu aslında bazı istemcilerin uygulamayı sürekli olarak kesilen tehlikeli bir kablosuz bağlantıyla kullandığı için oluyor. "Son kullanıcıların uygulamanızı kırmanın yollarını bulma yeteneklerini asla küçümseme" sözü var, burada kesinlikle doğrudur :-)
Sunday Ironfoot

@qwertypants - Hayır, internet bağlantısı kesildiğinde hiçbir şey olmuyor (örneğin, kablonun çıkarılması). $ .Ajax denemesi yapılsa da Firebug'da görebiliyorum.
Pazar

Bağlantı girişimi için zaman aşımını ayarlamanın bir yolu var mı?
axk

Yanıtlar:


100
// start snippet
error: function(XMLHttpRequest, textStatus, errorThrown) {
        if (XMLHttpRequest.readyState == 4) {
            // HTTP error (can be checked by XMLHttpRequest.status and XMLHttpRequest.statusText)
        }
        else if (XMLHttpRequest.readyState == 0) {
            // Network error (i.e. connection refused, access denied due to CORS, etc.)
        }
        else {
            // something weird is happening
        }
    }
//end snippet

4
Kabul edilen cevap bu olmalıdır. $ .Ajax'a sağladığınız hata fonksiyonunda, ilk parametre her türlü durum bilgisini sağlar. Bir zaman aşımı ayarlamasanız bile bunu yapar.
Mike Spear

Ve aynısını bir ajax formuyla yapmak için: <form ... data-ajax-failure="YourMethod" ...></form>ve sizin yönteminizlefunction YourMethod(XMLHttpRequest) { ..same code... }
Matthieu Charbonnier

1
Daha fazla bilgi XMLHttpRequest.readyStateiçin ajax_xmlhttprequest_response.asp
stomy

13

Sadece eklemelisiniz: timeout: <number of miliseconds>,içinde bir yerde $.ajax({}). Ayrıca, cache: false,birkaç senaryoda yardımcı olabilir.

$ .ajax iyi belgelenmiştir , oradaki seçenekleri kontrol etmelisiniz, yararlı bir şeyler bulabilir.

İyi şanslar!


1
Ajax'ta hiç belgelenmemiş ve bir şekilde gizlenmiş birçok şey var :(
Espanta

9

Sorunu tekrarlayamadığım için sadece ajax çağrısında zaman aşımı ile denemeyi önerebilirim. JQuery'de bunu $ .ajaxSetup ile ayarlayabilirsiniz (ve tüm $ .ajax aramalarınız için global olacaktır) veya aşağıdaki gibi aramanız için özel olarak ayarlayabilirsiniz:

$.ajax({
    type: 'GET',
    url: 'http://www.mywebapp.com/keepAlive',
    timeout: 15000,
    success: function(data) {},
    error: function(XMLHttpRequest, textStatus, errorThrown) {}
})

JQuery, aramanızda 15 saniyelik bir zaman aşımı kaydedecektir; bundan sonra sunucudan bir http yanıt kodu olmadan jQuery, hata geri aramasını textStatus değeri "zaman aşımı" olarak ayarlanmış şekilde yürütür. Bununla en azından ajax çağrısını durdurabilirsiniz, ancak gerçek ağ sorunlarını bağlantı kaybından ayırt edemezsiniz.


3

Bu durumda gördüğüm şey, eğer istemci makinenin ağ kablosunu çeker ve aramayı yaparsam, ajax başarı işleyicisi çağrılır (neden, bilmiyorum) ve veri parametresi boş bir dizedir. Yani gerçek hata işlemeyi hesaba katarsanız, şöyle bir şey yapabilirsiniz:

function handleError(jqXHR, textStatus, errorThrown) {
    ...
}

jQuery.ajax({
    ...
    success: function(data, textStatus, jqXHR) {
        if (data == "") handleError(jqXHR, "clientNetworkError", "");
    },
    error: handleError
});

1

Etki alanları arası yapıyorsanız Jsonp Kullan'ı arayın. aksi takdirde hata döndürülmez.


0

KULLANIM

xhr.onerror = function(e){
    if (XMLHttpRequest.readyState == 4) {
        // HTTP error (can be checked by XMLHttpRequest.status and XMLHttpRequest.statusText)
        selFoto.erroUploadFoto('Erro HTTP: '+XMLHttpRequest.statusText);
    }
    else if (XMLHttpRequest.readyState == 0) {
        // Network error (i.e. connection refused, access denied due to CORS, etc.)
        selFoto.erroUploadFoto('Erro de rede:'+XMLHttpRequest.statusText);
    }
    else {
        selFoto.erroUploadFoto('Erro desconhecido.');
    }

};

(daha fazla kod aşağıdadır - RESİM ÖRNEĞİNİ YÜKLE)

var selFoto = {
   foto: null,

   upload: function(){
        LoadMod.show();

        var arquivo = document.frmServico.fileupload.files[0];
        var formData = new FormData();

        if (arquivo.type.match('image.*')) {
            formData.append('upload', arquivo, arquivo.name);

            var xhr = new XMLHttpRequest();
            xhr.open('POST', 'FotoViewServlet?acao=uploadFoto', true);
            xhr.responseType = 'blob';

            xhr.onload = function(e){
                if (this.status == 200) {
                    selFoto.foto = this.response;
                    var url = window.URL || window.webkitURL;
                    document.frmServico.fotoid.src = url.createObjectURL(this.response);
                    $('#foto-id').show();
                    $('#div_upload_foto').hide();           
                    $('#div_master_upload_foto').css('background-color','transparent');
                    $('#div_master_upload_foto').css('border','0');

                    Dados.foto = document.frmServico.fotoid;
                    LoadMod.hide();
                }
                else{
                    erroUploadFoto(XMLHttpRequest.statusText);
                }

                if (XMLHttpRequest.readyState == 4) {
                     selFoto.erroUploadFoto('Erro HTTP: '+XMLHttpRequest.statusText);
                }
                else if (XMLHttpRequest.readyState == 0) {
                     selFoto.erroUploadFoto('Erro de rede:'+XMLHttpRequest.statusText);                             
                }

            };

            xhr.onerror = function(e){
            if (XMLHttpRequest.readyState == 4) {
                // HTTP error (can be checked by XMLHttpRequest.status and XMLHttpRequest.statusText)
                selFoto.erroUploadFoto('Erro HTTP: '+XMLHttpRequest.statusText);
            }
            else if (XMLHttpRequest.readyState == 0) {
                 // Network error (i.e. connection refused, access denied due to CORS, etc.)
                 selFoto.erroUploadFoto('Erro de rede:'+XMLHttpRequest.statusText);
            }
            else {
                selFoto.erroUploadFoto('Erro desconhecido.');
            }
        };

        xhr.send(formData);
     }
     else{
        selFoto.erroUploadFoto('');                         
        MyCity.mensagens.push('Selecione uma imagem.');
        MyCity.showMensagensAlerta();
     }
  }, 

  erroUploadFoto : function(mensagem) {
        selFoto.foto = null;
        $('#file-upload').val('');
        LoadMod.hide();
        MyCity.mensagens.push('Erro ao atualizar a foto. '+mensagem);
        MyCity.showMensagensAlerta();
 }
 };

-1

ağlarının kesilmesi veya sayfa güncellemesinin başarısız olması durumunda kullanıcıyı uyarmak için şunları yaptım:

  1. Sayfada geçerli saati koyduğum ve bu etiketi her 10 saniyede bir güncellediğim bir div etiketi var. Şuna benzer:<div id="reloadthis">22:09:10</div>

  2. Div etiketindeki zamanı güncelleyen javascript işlevinin sonuna şunu koyuyorum (zaman AJAX ile güncellendikten sonra):

    var new_value = document.getElementById('reloadthis').innerHTML;
    var new_length = new_value.length;
    if(new_length<1){
        alert("NETWORK ERROR!");
    }
    

Bu kadar! Elbette, uyarı bölümünü istediğiniz herhangi bir şeyle değiştirebilirsiniz. Bu yardımcı olur umarım.


-6

Bunu denedin mi

$(document).ajaxError(function(){ alert('error'); }

Bu, tüm AjaxErrors'ları işlemelidir. Onu burada buldum . Orada, bu hataları firebug konsolunuza yazma imkanı da bulacaksınız.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.