我正在为演示文稿准备一些示例材料,该演示文稿还涵盖了jQuery承诺的基础知识,并且我正在计算一些奇怪的行为。希望你们能帮我解决这个问题。
我有以下代码,完全正常。
var getHTML1 = $.ajax({
url: "jquerypromises.html",
type: "GET"
});
getHTML1.done(function(responseText, state, jqXHR){
console.log("success from AJAX request with promises : getHTML1!");
});
getHTML1.fail(function(){
console.log("error from AJAX request with promises : getHTML1!");
});
//this one will call the failure callback!!!!!!
var getHTML2 =
$.ajax({
url: "somenonexistingpage.html", //<== THIS WILL call the failure callback
type: "GET"
})
.then(
function(){
console.log("success from AJAX request with promises : getHTML2!");
}
,
function(jqXHR, state){
console.log("error from AJAX request with promises : getHTML2!");
}
);
此代码的运行与调用完成处理程序的getHTML1
相同,并且getHTML2
调用失败处理程序。
现在,当我在上面的代码下面添加以下代码时。
$.when(getHTML1, getHTML2).then(
function(response1, response2) {
// both arguments are arrays with[responseText, "success", jqXHR]
console.log("Both promises went successfull");
console.dir(response1);
console.dir(response2);
},
function(jqXHR, status) {
console.log("One of both promises went wrong!");
console.log(jqXHR);
console.log(status);
}
);
再次调用正确的处理程序。在这种情况下,正在调用失败回调,但它的所有参数都是未定义的。这是为什么?
现在当我删除then()
块中的失败处理程序时,getHTML2
的代码变为如下:
var getHTML2 =
$.ajax({
url: "somenonexistingpage.html", //<== THIS WILL call the failure callback
type: "GET"
})
.then(
function(){
console.log("success from AJAX request with promises : getHTML2!");
}
);
现在一切都按预期工作,第二个then()块中的失败处理程序被填充参数调用。
使用jQuery 1.9.1在Chrome中测试
答案 0 :(得分:0)
基本上,这是因为then()的文档说(强调我的):
这些过滤器功能可以返回要传递的新值 承诺的
.done()
或.fail()
回调,或者他们可以返回另一个 将通过它的可观察对象(延迟,承诺等) 已解决/拒绝的状态和承诺的回调值。如果 使用的过滤函数是null
,或未指定,承诺将 使用与原始相同的值来解析或拒绝。
因此,您可以从失败过滤器返回单个值,这不是您想要的(您需要两个值),或者完全省略失败过滤器以使then()
传递与原始承诺相同的值。
如果要实现一个返回多个值的失败过滤器,可以返回一个新的Deferred对象,您可以使用这些值立即拒绝该对象:
var getHTML2 = $.ajax({
url: "somenonexistingpage.html", //<== THIS WILL call the failure callback
type: "GET"
}).then(function() {
console.log("success from AJAX request with promises : getHTML2!");
}, function(jqXHR, state) {
console.log("error from AJAX request with promises : getHTML2!");
return $.Deferred().reject(jqXHR, state);
});