我有很多功能,目前看起来像这样:
function LoadFromURL(url)
{
var d = $.Deferred();
$.get(url).then(function(text)
{
LoadFromText(text).then(function(obj)
{
d.resolve(obj);
},
function(err)
{
d.reject(err);
});
},
function(err)
{
d.reject(err);
});
return d.promise();
}
此函数接受一个URL并在promise中加载文本。然后将文本传递给LoadFromText函数,该函数返回另一个promise。如果成功,则解决外部延迟。如果无法加载URL,或者LoadFromText函数失败,则拒绝外部延迟。
有没有办法可以将解决/拒绝的结果链接起来并最终得到这样的结果:
function LoadFromURL(url)
{
return $.get(url).then(function(text)
{
return LoadFromText(text);
},
function(err)
{
return $.Deferred().reject(err);
}).promise();
}
我已经看到一些承诺的实现允许这样做 - 在'then'中返回一个promise,意味着使用了promise的最终结果。
我意识到这暂时不起作用(结果是承诺,而不是承诺的结果),但希望有人可以建议一种方法来完成这项工作,这样我就可以整理有时令人困惑的混乱第一个例子。
我希望这是有道理的。感谢。
答案 0 :(得分:1)
有没有办法可以将结果链接
是的,这是then
的默认行为!
function LoadFromURL(url) {
return $.get(url).then(LoadFromText);
}
自1.8版以来,我已经看到一些承诺的实现允许这样做 - 在'then'中返回一个promise,意味着使用了promise的最终结果。
jQuery 支持此行为。对于1.5到1.7,您可以使用.pipe
。
答案 1 :(得分:0)
LoadFromURL
将简化如下:
function LoadFromURL(url) {
return $.get(url).then(function(text) {
return LoadFromText(text);
});
}
可能存在您未考虑过的问题......
与原始版本一样,该过程将倾向于无限递归,直到服务器返回HTTP错误。在适当地编写服务器资源时会遇到轻微的挑战,特别是如果可能需要访问最终提供的文本。
稍微考虑一下,您可以以文本本身或HTTP响应代码中指示“继续”或“完成”的方式传递所有文本。例如,您可以使用响应代码202(“已接受”)来指示该过程不完整。
我认为这会有效(使用jQuery 1.5+):
function LoadFromURL(url) {
return $.get(url).then(function(text, textStatus, jqXHR) {
if(jqXHR.status === 202) {//continue
return LoadFromText(text);
}
else {//complete
return text;
}
});
}
您只需要安排服务器返回202表示“继续”或200表示“完成”。
因此,可以按如下方式调用LoadFromURL():
LoadFromURL('my/resource').then(function(text) {
console.log("After a series of $.get requests, the finally delivered text was:\n" + text);
});
答案 2 :(得分:0)
我不确定我是否理解正确,因为你的第二个功能LoadFromText
对我来说是某种黑盒子。不过,我认为你的构造对于执行的事情来说太过臃肿了。尝试在更少的功能中执行此操作。我做了一个命题:
function Load() {
var myUrl = '//path.to/url';
LoadFromUrl(myUrl)
.then(LoadFromText, errorHandler)
.then(successHandler, errorHandler);
}
function successHandler(returnedData) {
console.log('Requests were successful: ' + returnedData);
}
function errorHandler(err) {
console.log('An error occurded: ' + err);
}
function LoadFromURL(url) {
return $.get(url);
}
function LoadFromText(text) {
// THIS IS SOME SORT OF BLACK BOX FOR ME...
// SEEMS TO RETURN A PROMISE, THOUGH
var $deferred = $.Deferred();
// DO THE LOGIC TO EITHER REJECT OR RESOLVE THE PROMISE
return $deferred.promise();
}
您只使用主函数Load
来启动ajax链。第一个ajax请求完成后,第二个以第一个ajax请求的数据开始。之后,successHandler将对第二个ajax调用的数据执行任何操作。这是您解决方案的重要补充
除此之外,它与您所做的基本相同,但分发给更易于维护的小功能。