4

我想以这种方式进行一堆 Ajax 调用: call(n) 在 call(n-1) 完成后开始......

我不能使用async:false有很多原因:

  • 一些请求可能是jsonp(最相关的)
  • 我还有其他可能同时工作的ajax请求..
  • 浏览器被屏蔽了

我不能以这种方式链接我的请求:

$.post('server.php', {param:'param1'}, function(data){
        //process data
    $.post('server.php', {param:'param2'}, function(data){
        //process data
    });
});

因为请求的数量和参数是根据用户输入动态创建的。

一个小例子说明了我的问题。

你会看到服务器响应顺序是随机的,我想要实现的就是有序

Response to arg1
Response to arg2
Response to arg3
Response to arg4
Response to arg5
Response to arg6

任何帮助将不胜感激,谢谢。

4

2 回答 2

7

好的,jQuery Ajax返回一个Deferred Object,这可以帮助您实现这一点。

这是如何做到的:

var args = ['arg1','arg2','arg3','arg4','arg5','arg6'];

deferredPost(0, 5);

function deferredPost(index, max){    
    var delay = Math.random()*3;
    if (index<max){
        return $.post('/echo/html/', {html:('Response to '+args[index]), delay:delay}, 
        function(data){
            $('#response').append(data+'<br>');
        }).then(function(){
            deferredPost(index+1, max);
        });
    } else {
        return $.post('/echo/html/', {html:('Response to '+args[index]), delay:delay}, 
        function(data){
            $('#response').append(data+'<br>');
        });
    }
}

演示

这里我使用了then函数。

我还建议阅读更多关于延迟对象的内容,它们可以解决一些常见问题。

于 2012-06-11T13:33:30.903 回答
1

这是队列的工作。

var queue = ['arg1','arg2','arg3','arg4','arg5','arg6'];

function runQueueInOrder() {
    if (queue.length === 0) { return; }
    var arg = queue.pop();
    var delay = Math.random()*3;
    $.post('/echo/html/', {html:('Response to '+ arg), delay:delay}, 
        function(data){
            $('#response').append(data+'<br>');        
    }).then(function() {
        runQueueInOrder();
    });        
}

runQueueInOrder();

then如果您已将队列的处理封装在一个函数中,则无需使用 jQuery即可。不过它很方便。该代码具有破坏性,因为它从原始数组中删除了元素(但在处理它们时,通常没问题)。

调用该方法runQueueInOrder以启动处理。

当没有更多工作要做时,函数简单地退出。(我之前写过一个在计时器上轮询的版本,但这里不需要)。

该函数抓取下一个工作arg,调用您的post调用语法,并在完成后使用 jQuery 的 deferred then 回调再次调用该函数(如果需要进一步处理队列)。

(我查看了另一个答案,发现它难以理解,因此我采用了一种更简单的方法。使用我的简单版本,您可以在发现新作品时添加新项目 - 或删除它们。)。

于 2012-06-11T15:45:39.957 回答