我偶然发现了一段不是100%安全的Ajax代码,因为它混合了异步/同步类型的代码…所以基本上在下面的代码中我有一个jQuery.each,其中每个元素都获取有关元素的信息并启动Ajax收到每个请求:
$(search).each(function() { $.ajax({ url: 'save.x3?id='+$(this).attr("id")+'value='$(this).data("value"); success: function(o){ //Update UI }, error: function(o){ //Update UI } }); }); //code to do after saving...
因此,显然,“保存后要执行的代码…”通常在所有请求完成之前执行。在理想情况下,我想让服务器端代码一次处理所有这些代码,并保存成功回调后将//代码移到要执行的代码中,但是假设这不可能,我将代码更改为如下代码:确保所有请求都返回,然后再继续执行,而我仍然不喜欢:
var recs = []; $(search).each(function() { recs[recs.length] = 'save.x3?id='+$(this).attr("id")+'value='$(this).data("value"); }); var counter = 0; function saveRecords(){ $.ajax({ url: recs[counter], success: function(o){ //Update progress if (counter<recs.length){ counter++; saveRecords(); }else{ doneSavingRecords(); } }, error: function(o){ //Update progress doneSavingRecords(o.status); } }); } function doneSavingRecords(text){ //code to do after saving... } if (recs.length>0){ saveRecords(); //will recursively callback itself until a failed request or until all records were saved }else{ doneSavingRecords(); }
因此,我正在寻找向一系列异步调用中添加一些同步功能的“最佳”方法?
谢谢!!
更好的答案 :
function saveRecords(callback, errorCallback){ $('<div></div>').ajaxStop(function(){ $(this).remove(); // Keep future AJAX events from effecting this callback(); }).ajaxError(function(e, xhr, options, err){ errorCallback(e, xhr, options, err); }); $(search).each(function() { $.get('save.x3', { id: $(this).attr("id"), value: $(this).data("value") }); }); }
可以这样使用:
saveRecords(function(){ // Complete will fire after all requests have completed with a success or error }, function(e, xhr, options, err){ // Error will fire for every error });
原始答案 :如果它们需要按一定顺序排列,或者页面上有其他常规AJAX事件会影响的使用ajaxStop,则这样做会很好,但这会比较慢:
ajaxStop
function saveRecords(callback){ var recs = $(search).map(function(i, obj) { return { id: $(obj).attr("id"), value: $(obj).data("value") }; }); var save = function(){ if(!recs.length) return callback(); $.ajax({ url: 'save.x3', data: recs.shift(), // shift removes/returns the first item in an array success: function(o){ save(); }, error: function(o){ //Update progress callback(o.status); } }); } save(); }
然后您可以这样称呼它:
saveRecords(function(error){ // This function will run on error or after all // commands have run });