我有一个通用的泛型函数,它将用于ajax调用。在第一次触发时,我将从服务器获取整个数据,并且我将保持本地范围。所以在第二次,它不会是服务器的数据。在我的情况下,问题是第一个请求是异步请求,而处理第一个请求第二个请求即将到来,它正在命中服务器。现在,在第一个请求完成之前,如何将第二个请求置于等待状态?
a.js
会调用具有ajax调用的call.js
:get();
b.js
也会调用相同的函数。在第二个数据中,global
变量中提供了数据,因此它不会进行任何ajax调用:get();
call.js:
var get = function() {
var global = [];
if (Object.keys(global).length)
retrun global;
ajaxcall({
// ...
}).done(function(data) {
global = data;
}).fail(function(err) {
});
}
在这种情况下,处理第一个请求的第二个请求即将到来。所以它正在打另一个电话。
答案 0 :(得分:2)
只有一个请求运行到服务器,下一个请求必须等到第一个请求完成
这个问题需要更多行代码,之前已经得到了回答,所以我将链接到几个例子。您应该寻找的是关键字" ajax queue"。
我建议在这种情况下使用一个可用的库,但第一个答案也给出了一些无库代码的例子。
只有一个请求并缓存结果
通常首先要做的就是跟踪你现有的电话。
var isCallInProgress = false;
var global = [];
var get = function() {
if (Object.keys(global).length)
return global;
if (isCallInProgress)
return;
isCallInProgress = true;
ajaxcall({
// ...
}).done(function(data) {
global = data;
isCallInProgress = false;
}).fail(function(err) {
});
}
根据您的使用情况,您可能需要在此处进行一些进一步的工作。如果数据已经加载则立即返回数据,如果不是非常理想则不返回任何内容。像这样的东西会更符合通常预期的API设计:
var isCallInProgress = false;
var global = [];
var get = function(returnCallback) {
if (Object.keys(global).length){
// callback immediately
// you might also want to wrap this in a promise or setTimeout, depending on your expected behavior
returnCallback(global);
}
if (isCallInProgress)
return;
isCallInProgress = true;
ajaxcall({
// ...
}).done(function(data) {
global = data;
isCallInProgress = false;
// async callback
returnCallback(global);
}).fail(function(err) {
// error callback would probably also be appreciated by the caller
});
}
答案 1 :(得分:1)
您可以在ajax调用中使用async: false
,但不推荐使用此功能。最好的想法是创建一个控件var。
var requestSucceded = false;
var get = function() {
var global = [];
if (Object.keys(global).length && requestSucceded)
return global;
ajaxcall({
// ...
}).done(function(data) {
global = data;
requestSucceded = true;
}).fail(function(err) {
});
}
答案 2 :(得分:0)
在第一次请求的回调中执行第二次请求。
var get = function() {
var global = [];
if (Object.keys(global).length)
retrun global;
ajaxcall({
// ...
}).done(function(data1) {
global = data1;
//perform second request here, return data2
}).fail(function(err) {
});
}
第二个请求不会执行,直到第一个请求成功并调用其回调。
答案 3 :(得分:0)
您可以use Promises API以优雅的方式解决此问题。
//call.js
var DataPromise = new Promise(function(resolve, reject) {
ajaxcall({
// ...
}).done(resolve).fail(reject);
});
//a.js
DataPromise.then(function(data) { console.log("a.js now has the data"); });
//b.js
DataPromise.then(function(data) { console.log("b.js now has the data"); });
Promises API将负责跟踪DataPromise
的状态,并确保只发出一次ajaxcall。
答案 4 :(得分:0)
jQuery中的$.ajax
函数返回一个jQuery XMLHttpRequest对象或jqXHR。该对象可以存储,并且可以在其上运行函数。
最好的选择是将返回的jqXHR或XMLHttpRequest存储在全局可访问的变量中。在这两个函数中的每个函数中,检查该全局可访问变量是否为null。如果是,则运行它。 ajaxcall完成后,清除varname:
varname = ajaxcall({
// ...
})
// ...
.always(function(){
varname = null;
);