Неожиданное поведение с setTimeout

0

Я внедрил функцию опроса ajax, которую мне нужно звонить непрерывно, пока результаты опроса не вернутся с моими ожидаемыми результатами. Для этого я использую setTimeout чтобы ввести задержку, чтобы функция не просто забивала сервер запросами, пока не получила результаты.

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

Вот рабочий код, который успешно устанавливает тайм-аут и опросы для результата:

function makeRequest(url, data, requestType, successCallback, errorCallback, doneCallback) {
    $.ajax({
        url: url,
        type: requestType,
        data: data != null ? JSON.stringify(data) : '',
        contentType: 'application/json; charset=utf-8',
        success: function (success) {
            if (successCallback) successCallback(success);
        },
        error: function (error) {
            if (errorCallback) errorCallback(error);
        },
        done: function() {
            if (doneCallback) doneCallback();
        }
    });
}

function pollForResult(Id) {
    setTimeout(function () {
        makeRequest('/Transaction/TransactionResult/' + Id,
            null,
            "GET",
            function(result) {
                //success code here
            }, function(error) {
                //error callback implementation here
                if (error.status === 404) {
                    pollForResult(Id); //results not ready, poll again.
                } else {
                    alert("stopped polling due to error");
                }
            }, null);
    }, 2000);
}

Вот код, который неправильно устанавливает тайм-аут и просто постоянно обращается к серверу с запросами:

function pollForResult(Id) {
    makeRequest('/Transaction/TransactionResult/' + Id,
        null,
        "GET",
        function(result) {
            //success code here
        }, function(error) {
            //error callback implementation here
            if (error.status === 404) {
                setTimeout(pollForResult(Id), 2000); //results not ready, poll again.
            } else {
                alert("stopped polling due to error");
            }
       }, null);
}

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

Я подозреваю, хотя я и не пробовал, что это будет правильно работать во втором блоке кода:

setTimeout(function(){ pollForResult(Id); }, 2000); //results not ready, poll again.
Теги:
settimeout

1 ответ

3
Лучший ответ
setTimeout(pollForResult(transactionId),2000);

Этот код немедленно вызывает pollForResult и назначает его возвращаемое значение функцией, вызываемой при возникновении таймаута.

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

Как вы сказали, function() {pollForResult(transactionId);} будет работать нормально.

  • 0
    +1, вы также можете использовать Function.prototype.bind () : setTimeout(pollForResult.bind(null, transactionId), 2000); если вы предпочитаете более короткий синтаксис. (Примечание: он требует IE 9+, если вы не используете polyfill ).
  • 1
    @ComFreek И причина, по которой это работает, в том, что .bind() возвращает функцию (замыкание) ^ _ ^

Ещё вопросы

Сообщество Overcoder
Наверх
Меню