Подтвердить что ты не робот

Отмените вызов jQuery AJAX до его возвращения?

У меня есть диалоговое окно jQuery, которое открывается, а затем выполняется вызов AJAX. Я хотел бы сделать так, чтобы, если диалоговое окно закрыто или нажата кнопка отмены, вызов AJAX отменяется, и его функция обратного вызова не вызывается. Я могу придумать некоторые способы сделать это с такой переменной:

  function doStuff(){
    var doCallback = true;
    $('#dialog').dialog({
      title: 'Dialog Title',
      modal: true,
      buttons: {
        Cancel: function() {
          doCallback = false;
          doSomethingElse();
        }
      }
    });
    $.get('url/url/url', function(data){
      if(doCallback){
        doTheSuccessThing(data);
      }
    });
  }

Но, так или иначе, это кажется мне грязным, и это фактически не прекращает вызов AJAX. Есть ли встроенный способ отмены вызова AJAX?

4b9b3361

Ответ 1

Хорошо, поэтому, основываясь на предположении использовать объект XmlHttpRequest, возвращаемый функцией $.get, я придумал следующее:

function doStuff(){
    var ajaxRequest = $.ajax({
                        url : 'url/url/url',
                        type : "GET",
                        success : function(data){
                          ajaxRequest = null;
                          doSuccessStuff(data);
                        }
                      });

    $('#dialog').dialog({
      title: 'Stuff Dialog',
      bgiframe: true,
      modal: true,
      buttons: {
        Cancel: function() {
          if (ajaxRequest)
            ajaxRequest.abort();
          doCancelStuff();
        }
      }
    });
  }

Кажется, он работает и чувствует себя более чистым для меня.

Ответ 2

Когда у меня есть обратный вызов, который может быть запущен несколько раз, но я хочу использовать только последний, я использую этот шаблон:

var resultsXHR, resultsTimer, resultsId=0;
$('input').keyup(function(){
  clearTimeout(resultsTimer);                     // Remove any queued request
  if (resultsXHR) resultsXHR.abort();             // Cancel request in progress
  resultsTimer = setTimeout(function(){           // Record the queued request
    var id = ++resultsId;                         // Record the calling order
    resultsXHR = $.get('/results',function(data){ // Capture request in progress
      resultsXHR = null;                          // This request is done
      if (id!=resultsId) return;                  // A later request is pending
      // ... actually do stuff here ...
    });  
  },500);                                         // Wait 500ms after keyup
});

Только abort() недостаточно для предотвращения вызова обратного вызова успеха; вы все равно можете найти свой обратный вызов, даже если вы попытались отменить запрос. Вот почему необходимо использовать трекер resultsId и завершить обработку обратного вызова, если другой, более поздний, перекрывающий обратный вызов готов к работе.

Учитывая, насколько это распространено и громоздко, я думаю, что это хорошая идея, чтобы обернуть его повторно используемым способом, который не требует, чтобы вы придумали уникальный триплет локальных имен переменных для каждого, с которым хотите обрабатывать

(function($){
  $.fn.bindDelayedGet = function(event,delay,url,dataCallback,dataType,callback){
    var xhr, timer, ct=0;
    return this.bind(event,function(){
      clearTimeout(timer);
      if (xhr) xhr.abort();
      timer = setTimeout(function(){
        var id = ++ct;
        xhr = $.get(url,dataCallback && dataCallback(),function(data){
          xhr = null;
          if (id==ct) callback(data);
        },dataType);
      },delay);
    });
  };
})(jQuery);

// In action
var inp = $('#myinput').bindDelayedGet('keyup',400,'/search',
  function(){ return {term:inp.val()}; },
  'html',
  function(html){ $('#searchResults').clear().append(html); }
);

Вы можете найти приведенный выше код более подробно на моем веб-сайте.

Ответ 3

В jQuery нет метода, но вы можете просто использовать объект XmlHttpRequest, возвращенный из функций jQuery get/post/ajax.

Из jQuery blog:

// Perform a simple Ajax request
var req = $.ajax({
  type: "GET",
  url: "/user/list/",
  success: function(data) {
    // Do something with the data...
    // Then remove the request.
    req = null;
  }
});

// Wait for 5 seconds
setTimeout(function(){
  // If the request is still running, abort it.
  if ( req ) req.abort();
}, 5000);

Ответ 4

Так кажется, хотя я никогда этого не делал.

$.get возвращает объект XmlHttpRequest, который имеет метод abort(), который вы можете вызвать. Может быть, попробуйте это?

Ответ 5

Если вы помещаете условие в script, вы ajax, где при условии, что true, вы выводите свой html, иначе вы ничего не выводите, тогда вы можете сделать простой, если (html) проверить функцию успеха например:

$.ajax({
      type: "GET",
      url: "url.php",
      data: "data="+data,
      success: function(html)
          { 
              if(html){
              $("#container").empty().html(html);
              }
      }
});

в этом примере url.php может выглядеть примерно так:

$data = $_GET['data'];

if($data=="whatever"){
     echo "<div>Hello</div>";
}else{}

Это сработало для меня. Я знаю, что это сообщение устарело, но надеюсь, что это поможет кому-то.