Организация очереди запросов через jQuery.Deferred()

176
12 декабря 2016, 10:00

По нажатию на кнопку идет post запрос, который возвращает html со скриптами, содержание которого зависит от параметров (param).

function GetPlaces(param) {
    $.post(places_url, param, function(data) {
        $(".places").html(data);
    });
}

При быстрой смене параметров и многократном нажатии на кнопку отрисовка выполняется естественно не порядке нажатия на кнопку. Нужно реализовать нечто вроде очереди (чтобы при повторном нажатии на кнопку отправка происходила, только после полной отрисовки и выполнения всех скриптов первого нажатия.

Пытаюсь сделать так, но желаемого результата нет:

defPlaces = $.Deferred();
function GetPlaces(param) {
    defPlaces = defPlaces.then(
        $.post(places_url, param, function(data) {
            $(".places").html(data);
        })
    );
}

Что я делаю не так?

Answer 1

Конструкция, которую вы предложили, выглядит очень странно. Как минимум, отдавать важную часть управляющей конструкции с сервера при каждом запросе - неправильно.

В вашей исходной конструкции было три ошибки:

  1. Вы не вызвали нигде метод resolve (по-хорошему, его надо было вызвать сразу же). Также для создания изначально заресолвленного промиза можно воспользоваться методом when.
  2. Вы не передали в метод then функцию для обратного вызова.
  3. Вы не ждете окончания выполнения запроса. Для того, чтобы промиз, используемый в качестве очереди, оказался заресолвлен только по окончанию запроса - надо вернуть этот самый запрос из колбека then.

Вот итоговый код:

defPlaces = $.when();
function GetPlaces(param) {
    defPlaces = defPlaces.then(function () {
        return $.post(places_url, param, function(data) {
            $(".places").html(data);
        })
    });
}
Answer 2

Сработала следующая конструкция:

defPlaces = $.Deferred();
function GetPlaces(param) {
    defPlaces.done(function() { setPlaces(param); });
}
function setPlaces(param) {
    defPlaces = $.Deferred();
     $.post(places_url, param, function(data) {
        $(".places").html(data);
      });
}

В html, который возвращается в post, после выполнения всех скриптов добавить:

defPlaces.resolve();
READ ALSO
Проверка checkbox jquery

Проверка checkbox jquery

Добрый день! Хочу подвесить обработчик на checkbox, для этого решил проверить его состояние при клике на checkbox, те

189
jQuery Selectric

jQuery Selectric

Пытаюсь с помощью Selectric выбрать текущий (выбранный) элемент LI, но ничего не получается, подскажите кто знает как это можно сделать

237
Как улучшить код и избавиться от множества if

Как улучшить код и избавиться от множества if

Вопросы по оформлению кода

308
Получить значение из объекта объектов

Получить значение из объекта объектов

Запутался в этих объектах, имея следующее, как получить значение id?

321