我需要在不锁定浏览器的情况下发出一系列N ajax请求,并希望使用jquery延迟对象来完成此任务.
下面是三个请求一个简单的例子,但我的程序可能需要超过100个排队(注意,这是不准确的使用情况下,实际的代码确实需要确保步骤执行下一之前成功(N-1)步):
$(document).ready(function(){
var deferred = $.Deferred();
var countries = ["US", "CA", "MX"];
$.each(countries, function(index, country){
deferred.pipe(getData(country));
});
});
function getData(country){
var data = {
"country": country
};
console.log("Making request for [" + country + "]");
return $.ajax({
type: "POST",
url: "ajax.jsp",
data: data,
dataType: "JSON",
success: function(){
console.log("Successful request for [" + country + "]");
}
});
}
Run Code Online (Sandbox Code Playgroud)
这是写入控制台的内容(所有请求都是并行进行的,响应时间与每个国家/地区的数据大小成正比:
Making request for [US]
Making request for [CA]
Making request for [MX]
Successful request for [MX]
Successful request for …Run Code Online (Sandbox Code Playgroud) 鉴于这些功能:
function func1() {
var dfd = $.Deferred();
setTimeout(function() {
dfd.resolve('Password');
}, 1000);
return dfd.promise();
}
function func2(message) {
var dfd = $.Deferred();
setTimeout(function() {
if (message == 'Password') {
dfd.resolve('Hello World');
}
}, 1000);
return dfd.promise();
}
Run Code Online (Sandbox Code Playgroud)
我想找到一个更好的方法来做到以下几点.注意这是使用jQuery 1.8.x.
var promise = func1();
promise.done(function(message1) {
var promise2 = func2(message1);
promise2.done(function(message2) {
alert(message2);
});
});
Run Code Online (Sandbox Code Playgroud)
有任何想法吗?我认为使用jQuery #pipe或#then会起作用,但我无法弄明白.这是一个小提琴:http://jsfiddle.net/Z7prn/
我正在使用我可用的REST API服务访问我的网站,它允许我首先进行身份验证,然后使用该身份验证的会话返回值来执行进一步的API调用.我可以正常访问它,没有任何问题.会话在一小时后超时.让我们说我想在一小时后进行API调用,我想重新进行身份验证并继续进行首先发生的AJAX调用.您是否可以建议我如何重做一个AJAX调用,如果会话超时,则首先进行身份验证,然后再继续使用原来的AJAX调用?
$.ajax({
type: "GET",
dataType: "json",
url: "url",
cache: false,
async: false,
success: function (data) {
alert(data);
},
error: function(xhr, textStatus, errorThrown) {
//$.ajax(this);
//return;
},
statusCode: {
403: function() {
var session = retryLogin();
if(session !== "")
{
// call this function again? How can we achieve this?????
}
}
}
});
Run Code Online (Sandbox Code Playgroud)
请告诉我如何再次调用那个应该首先运行的ajax调用?
编辑: 基本上我有两个AJAX调用,一个用于获取会话ID的身份验证,另一个用于根据该会话ID获取一些数据.如果会话ID在中途到期,我想重做身份验证调用,然后继续进行首先发生的AJAX调用.有关如何实现这一目标的任何建议?
我还添加了一个图表,以显示我想要实现的目标.

干杯.
我问这个问题所以我可以学习用javascript做某事的'最佳实践'方式.说我在这里有这个代码:
var someFunc = function () {
if (something) {
// do something
}
if (somethingElse) {
// do somethingElse
}
};
Run Code Online (Sandbox Code Playgroud)
问题是什么是确保在'somethingElse'之前始终运行'某事'的最佳方法.由于javascript是异步的,我知道我需要某种回调系统来确保这一点.但是,有没有更简单的方法来重构这个?如果有很多if语句怎么办?什么是最好的图书馆干净利落地做这样的事情?提前致谢.
我一直在阅读有关jquery中Promises的大量文章,并在发出多个ajax请求时避免了“回调地狱”。
我觉得但即使读这一切后,有被给予使用什么没有简单的答案-来讲.done(),.then()和.when()-在链接请求的条款。
我试图构建最基本的示例来说明我的观点。下面的代码可以完全按照我的要求运行,但是它唯一依赖的是.done(),我看不到其他方法(例如.then()或.when())适合什么位置。
因此,我创建了3个PHP脚本,并使用PHP的sleep方法来人为地延迟这些脚本完成所需的时间。延迟设置如下:
r1.php - 5秒r2.php - 1秒r3.php -3秒脚本本身就是这样简单:
<?php
// r1.php
echo "starting r1.php \n";
sleep(5); // Delay execution. Varies as described above for each script
echo "ending r1.php \n";
?>
Run Code Online (Sandbox Code Playgroud)
因此,如果这些被并行运行,顺序,他们会完成会r2.php,r3.php话r1.php。
但是,如果我们想为了运行这些东西(r1.PHP, ,r2.php),r3.php并有jQuery的等待,直到每个AJAX请求之前就进入下一个做?例如,如果某物r2.php取决于r1.phpetc 的结果。
我写了以下内容-正是这样:
$(document).ready(function() {
$.ajax({
url: 'ajax/r1.php',
method: 'get'
}).done(function(response1) { …Run Code Online (Sandbox Code Playgroud) 我正在尝试解决这个 js/async 场景,并且我想知道 js 世界的其他部分如何处理这个问题。
function doStuff(callback) {
cursor.each(function(err, blahblah) {
...doing stuff here takes some time
});
... Execute this code ONLY after the `cursor.each` loop is finished
callback();
Run Code Online (Sandbox Code Playgroud)
编辑
这是一个更具体的示例,使用下面的大部分建议进行了更新,但仍然不起作用。
function doStuff(callback) {
MongoClient.connect(constants.mongoUrl, function(err, db) {
var collection = db.collection('cases2');
var cursor = collection.find();
var promises = []; // array for storing promises
cursor.each(function(err, item) {
console.log('inside each'); // NEVER GETS LOGGED UNLESS I COMMENT OUT THIS LINE: return Q.all(promises).then(callback(null, items));
var def = Q.defer(); // Create …Run Code Online (Sandbox Code Playgroud)