2013-02-21 14 views
1

我想使用Deferred來正確地命令刪除對API的調用。與項目和圖像的應用程序處理:我的jQuery Deferred()用法有什麼問題?

Item: 
ItemId 

Images: 
ImageId 
ItemId 

所以圖片必須是與可刪除相關的項目之前被刪除,否則我DeleteItem()Ajax調用將在數據對象返回一個錯誤。

在下面的代碼中,我試圖在任何DeleteItem()ajax調用之前將所有的DeleteImage()ajax調用分組。

var deferreds1 = []; 
var deferreds2 = []; 

... 
// push()ing an unknown number of DeleteImage() ajax calls to deferred1 
// push()ing an unknown number of DeleteItem() ajax calls to deferred2 
... 

if (deferreds1.length > 0) { 
    $.when 
     .apply($, deferreds1) 
     .then(function(){ 
      console.log('deferred1 then'); 
      $.when 
        .apply($, deferreds2) 
        .then(function() { 
         console.log('deferred2 then'); 
        }) 
        .fail(function() { 
         console.log('deferred2 fail'); 
        }); 
      }) 
     .fail(function(){ 
       console.log('deferred1 fail'); 
     }); 
} 

function DeleteItemImage() { 
    var dfd = $.Deferred(); 

    $.ajax({ 
     ... 
     success: function (data) { 
      if (!data.success) { 
       alert('error'); 
      } 
      dfd.resolve(); 
     } 
     ... 
    }); 

    return dfd.promise(); 
} 

function DeleteItem() { 
    var dfd = $.Deferred(); 

    $.ajax({ 
     ... 
     success: function (data) { 
      if (!data.success) { 
       alert('error'); 
      } 
      dfd.resolve(); 
     } 
     ... 
    }); 

    return dfd.promise(); 
} 

看起來大部分時間都是按照預定的順序進行的,但並非總是這樣。幫助我找到我確信我錯過的一個小細節。

回答

1

看起來您在致電DeleteItem函數之前已解決所有DeleteItemImage延遲。我認爲你需要這樣做。

var deferreds1 = []; 
var deferreds2 = []; 

... 
// push()ing an unknown number of DeleteImage() ajax calls to deferred1 
// do not call DeleteItem here. Wait until all of deferreds1 are resolved. 
... 

if (deferreds1.length > 0) { 
    $.when 
     .apply($, deferreds1) 
     .done(function(){ 
      console.log('deferred1 done'); 
      // NOW call DeleteItem and add to deferreds2, 
      // since now all the Images are deleted. 
      deferreds2.push(DeleteItem()); // for each item... 
      $.when 
        .apply($, deferreds2) 
        .done(function() { 
         console.log('deferred2 done'); 
        }) 
        .fail(function() { 
         console.log('deferred2 fail'); 
        }); 
      }) 
     .fail(function(){ 
       console.log('deferred1 fail'); 
     }); 
}