簡體   English   中英

在下一個ajax調用之前等待ajax完成

[英]waiting for ajax to complete before next ajax call

我試圖等待ajax調用完成保存模型,然后再在列表中保存下一個模型。 我在四處搜尋,看到了一些有關延遲對象的內容,這些對我來說是新的,還有另一個具有遞歸功能的答案可以做到這一點。 我嘗試了遞歸方法,因為它似乎比使用延遲對象和使用$.when.apply($, arrayOfAjaxCalls).then()更有意義。 這樣的代碼(遞歸代碼如下):

    saveModel(index, numRequests) {
        var self = this;

        if (index < numRequests) {
            var sample = self.samplesToSave[index];    

            return $.ajax({
                url: model.url,
                contentType: "application/json",
                type: "POST",
                data: JSON.stringify(model),
                crossDomain: $.support.cors,
                xhrFields: {
                    withCredentials: $.support.cors,
                },
                success: function(data) {
                    console.log("JUST SAVED");
                    console.log(data);
                },
                error: function(xhr: any) {
                    console.log(xhr);
                },
            }).then(() => {
                self.saveModel(index + 1, numRequests);
            });
        }
    }

我這樣稱呼:

saveModel(0, _.size(myCollection)

在調用下一個saveModel之前,它實際上並不等待ajax調用完成其當前狀態。 基本上,它只是按順序為集合中的每個項目同步調用saveModel。 對我想念的東西有什么想法嗎? 如果$ .Deferred有更好的解決方案,我也可以。 謝謝。

編輯:對不起,它的意思是在saveModel函數的最后一行說saveModel。 試圖擺脫特定領域的部分。 我使用的是打字稿,不是咖啡稿

新嘗試:

    saveSampleNew() {
        var d = $.Deferred();
        d.resolve();
        var p = d.promise();
        var self = this;
        self.samplesToSave.forEach(sample => p = p.then(() => self.makeSaveRequest(sample)));

        return p;
    }

     makeSaveRequest(sample) {
        var self = this;

        return $.ajax({
            url:  "samples",
            contentType: "application/json",
            type: "POST",
            data: JSON.stringify(sample),
            crossDomain: $.support.cors,
            xhrFields: {
                withCredentials: $.support.cors,
            },
            success: function(data) {
                console.log("SAVED12");
                console.log(data);                    
            },
        });
    }

因為此代碼依賴於其他異步調用的完成,所以我將這種新嘗試稱為:

this.saveContainers(project).then(() => {

}).done(() => {
    self.saveSampleNew();
});

不,它應該以這種方式工作。 如果您認為它沒有等待,請提供更多有關如何調用它以及同步遞歸的體驗的信息。

但是遞歸調用有一個問題:

.then(function() {
  self.saveModel(index + 1, numRequests);
})

then和隨后通過saveModel方法返回的promise確實會通過第一個ajax調用直接解析,它不會等待遞歸鏈。 其他ajax調用仍在發生(按預​​期順序),但是沒有被所產生的promise跟蹤。

為了實現這一點,並正確地鏈接 promise,以便其以最后一個(“ innermost”)promise的結果進行解析,您需要將promise從回調returnthen

.then(function() {
  return self.saveModel(index + 1, numRequests);
})

通常,我可能會在這里使用for循環而不是遞歸調用-我發現在這種情況下更容易閱讀。

saveModel() {
     var d = $.Deferred(); d.resolve();
     var p = d.promise(); // to start the chain
     this.samplesToSave.forEach(sample => p = p.then(() => makeSaveRequest(sample));
     return p;
}

makeSaveRequest(sample) {
    return $.ajax({...}); // make request using `sample` as data
} 

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM