Vorherige Ajax-Anfrage bei neuer Anfrage abbrechen

77

Ich habe eine Funktion, die beim Ändern einer Eingabe einen Ajax-Aufruf ausführt.

Es besteht jedoch die Möglichkeit, dass die Funktion erneut ausgelöst wird, bevor der vorherige Ajax-Aufruf abgeschlossen wurde.

Meine Frage ist, wie würde ich den vorherigen Ajax-Aufruf abbrechen, bevor ich einen neuen beginne? Ohne Verwendung einer globalen Variablen. (Siehe Antwort auf eine ähnliche Frage hier )

jsfiddle meines aktuellen Codes:

Javascript:

var filterCandidates = function(form){
    //Previous request needs to be aborted.
    var request = $.ajax({
        type: 'POST',
        url: '/echo/json/',
        data: {
            json: JSON.stringify({
                count: 1
            })
        },
        success: function(data){
            if(typeof data !== 'undefined'){
                jQuery('.count').text(data.count)
                console.log(data.count);
            }
        }
    });
};

if(jQuery('#search').length > 0){
    var form = jQuery('#search');
    jQuery(form).find(':input').change(function() {
        filterCandidates(form);
    });
    filterCandidates(form);
}

HTML:

<form id="search" name="search">
    <input name="test" type="text" />
    <input name="testtwo" type="text" />
</form>
<span class="count"></span>
CharliePrynn
quelle
Ihr Fragentitel ist falsch. Es sollte sein, dass eine neue AJAX-Anfrage abgebrochen wird, bevor die vorherige abgeschlossen wird
Abhishek Kamal

Antworten:

109
 var currentRequest = null;    

currentRequest = jQuery.ajax({
    type: 'POST',
    data: 'value=' + text,
    url: 'AJAX_URL',
    beforeSend : function()    {           
        if(currentRequest != null) {
            currentRequest.abort();
        }
    },
    success: function(data) {
        // Success
    },
    error:function(e){
      // Error
    }
});
Siva.Net
quelle
12
sollten nicht beide Response-Handler ( successund error) currentRequestzurückgesetzt werden null?
CodeManX
3
OP fragte how would I abort the previous ajax call. Aber hier brechen Sie currentRequestdie neuere ab. Somit wird die vorherige ausgeführt, die neue Anforderung wird abgebrochen. Richtig?
Phil294
10
ah nein. beforeSendwird ausgeführt, bevor das jqXHRObjekt zugewiesen wird currentRequest. Somit wird der vorherige Anruf dort abgebrochen. - schätzen immer gut kommentierte Antworten
phil294
5
Diese Lösung funktioniert bei mir nicht im GET-Typ. Ich habe nicht bei POST nachgefragt.
Sanyam Jain
4
Während dieser Code die Frage möglicherweise beantwortet, würde die Bereitstellung eines zusätzlichen Kontexts darüber, wie und warum das Problem gelöst wird, den langfristigen Wert der Antwort verbessern.
Alexander
10
var filterCandidates = function(form){
    //Previous request needs to be aborted.
    var request = $.ajax({
        type: 'POST',
        url: '/echo/json/',
        data: {
            json: JSON.stringify({
                count: 1
            })
        },
        success: function(data){
            if(typeof data !== 'undefined'){
                jQuery('.count').text(data.count)
                console.log(data.count);
            }
        }
    });
    return request;
};

var ajax = filterCandidates(form);

Speichern Sie in einer Variablen und überprüfen Sie diese vor dem zweiten Senden readyStateund rufen Sie sie abort()bei Bedarf auf

Romko
quelle
7
Das war einfacher als ich es mir vorgestellt hatte. Ich habe eine Geige dieser Arbeit erstellt: jsfiddle.net/YzDBg/4 für alle, die interessiert sind. Vielen Dank.
CharliePrynn
7
Können Sie das bitte näher erläutern?
SSS
5

eine Variation der akzeptierten Antwort und aus einem Kommentar zur Frage übernommen - das hat bei meiner Bewerbung hervorragend funktioniert ....

mit jQuerys $ .post () ....

var request = null;

function myAjaxFunction(){
     $.ajaxSetup({cache: false}); // assures the cache is empty
     if (request != null) {
        request.abort();
        request = null;
     }
     request = $.post('myAjaxURL', myForm.serialize(), function (data) {
         // do stuff here with the returned data....
         console.log("returned data is ", data);
     });
}

Rufen Sie myAjaxFunction () so oft auf, wie Sie möchten, und alle bis auf die letzte werden gelöscht (meine Anwendung verfügt über eine Datumsauswahl und ändert den Preis abhängig von den ausgewählten Tagen - wenn jemand ohne den obigen Code schnell darauf klickt, ist dies der Fall ein Münzwurf, ob sie den richtigen Preis bekommen oder nicht. Damit 100% richtig!)

CFP-Unterstützung
quelle
0

Versuchen Sie diesen Code

var lastCallFired=false;

var filterCandidates = function(form){

    if(!lastCallFired){
    var request = $.ajax({
        type: 'POST',
        url: '/echo/json/',
        data: {
            json: JSON.stringify({
                count: 1
            })
        },
        success: function(data){
            if(typeof data !== 'undefined'){
                jQuery('.count').text(data.count)
                console.log(data.count);
            }
        }
    });
        setInterval(checkStatus, 20);

    }

};

if(jQuery('#search').length > 0){
    var form = jQuery('#search');
    jQuery(form).find(':input').change(function() {
        filterCandidates(form);
    });
    filterCandidates(form);
}

var checkStatus = function(){
        if(request && request.readyState != 4){
            request.abort();
        }
    else{
        lastCallFired=true;
    }
};
Murali Murugesan
quelle
0
if(typeof window.ajaxRequestSingle !== 'undefined'){
  window.ajaxRequestSingle.abort();
}

window.ajaxRequestSingle = $.ajax({
  url: url,
  method: 'get',
  dataType: 'json',
  data: { json: 1 },
  success: function (data) {
    //...
  },
  complete: function () {
    delete window.ajaxRequestSingle;
  }
});
Arthur Shlain
quelle