我遇到了使用jQuery.when()等待多个ajax请求完成之后再调用另一个函数的问题。
每个ajax请求都会获得JSON数据,看起来像这样:
function loadData(arg){
var ajaxCall = $.ajax(
URL // depends on arg
)
.error( .... );
return ajaxCall;
}
调用请求时,返回值(ajaxCall)将添加到名为ajaxRequests的列表中。
ajaxRequests = [];
ajaxREquests.push(loadData(arg))
当所有请求都发出后,我正在尝试将ajaxRequests传递给$ .when,以便等待所有请求完成。
var defer = $.when.apply($, ajaxRequests);
defer.done(function(args){
for (var i=0; i<args.length; i++){
inst.loadData($.parseJSON(args[i].responseText));
}
inst.draw();
});
inst是一个基于JSON数据加载和绘制图形的对象。
问题是它似乎并没有真正等待请求完成 - args [i]是一个对象,但是代码运行时,responseText是未定义的。如果我保存args [i]并稍后从控制台访问它,它就可以工作。
我怀疑这个问题与使用.when和任意数量的参数有关,因为我在网上看到的所有例子都给它一个预定义的参数列表。
我不确定使用apply是否是正确的想法,但无论哪种方式都无法正常运行且行为不正常(取决于浏览器)。
非常感谢任何帮助。
如果需要更多信息,请与我们联系 我正在使用jQuery 1.5
答案 0 :(得分:35)
尽管亚历克斯确实为他的问题提供了解决方案,但我发现它有点困难。我遇到了与他解决的问题类似的问题,我希望与其他需要处理可变数量的ajax请求的人分享我的解决方案。
// Array of requests
var requests = Array();
requests.push($.get('responsePage.php?data=foo'));
requests.push($.get('responsePage.php?data=bar'));
var defer = $.when.apply($, requests);
defer.done(function(){
// This is executed only after every ajax request has been completed
$.each(arguments, function(index, responseData){
// "responseData" will contain an array of response information for each specific request
});
});
答案 1 :(得分:9)
除了Andy Corman的回答(我还是无法回复帖子,我认为......),如果你只有一个请求,响应信息将直接传递给defer.done - 作为一个参数;所以你需要为这种情况提供一个if:
// Array of requests
var requests = Array();
requests.push($.get('responsePage.php?data=foo'));
var defer = $.when.apply($, requests);
defer.done(function(){
// This is executed only after every ajax request has been completed
if (requests.length == 1)
// "arguments" will be the array of response information for the request
else
$.each(arguments, function(index, responseData){
// "responseData" will contain an array of response information for each specific request
});
});
答案 2 :(得分:4)
我想我现在已经解决了 - 问题在于处理返回的参数。 .done只传递了三个参数 - 响应文本,状态和jqXHR对象。我希望它能够传递每个查询产生的jqXHR对象。
我已经通过将每个查询的回调代码移动到一个单独的函数(即loadData中的ajax调用现在指定了执行'.loadData(...)'调用的回调函数)来解决它。由.done调用完成的事情是inst.draw()。这似乎工作正常:单独的回调都是在.done()之前执行的。
我不确定这是不是应该如何运作,但它似乎正在完成这项工作。
答案 3 :(得分:1)
尝试ajaxStart和ajaxStop,它们具有用于打开ajax请求的侦听器。
http://api.jquery.com/ajaxStart/ http://api.jquery.com/ajaxStop/