【发布时间】:2021-06-13 06:37:45
【问题描述】:
我刚刚开始使用 Javascript 和 Node,而异步和回调概念目前还不是我能控制的。
我必须为文档数组的每个元素调用一个函数。此函数将调用 DB 并为我获取文档注释数组。我想获取所有注释并将它们放在同一个数组上。类似的东西:
//function in an async waterfall
function(docs,callback){
let annotationsArray = [];
async.each(docs, (doc, callback2) => {
getAnnotationsFromDocument(doc.Id, callback2);
}, function (err,annotations){
if (err){
callback(err);
}
annotationsArray = annotationsArray.concat(annotations);
callback(null, annotationsArray);
});
},
//Next waterfall function
关于getAnnotationsFromDocument函数,这是它的简化结构:
function getAnnotationsFromDocument(docId,callback){
initDB();
var async = require('async');
async.waterfall([
function authorize(callback){
//checkAuthorization
(...)
},
function getRfpdocAnnotations(auth, metadata, callback){
//call to DB
(...)
},
function processRfpdocAnnotations(rfpDocAnnotations,metadata,callback){
(...)
callback(null,annotationsList);
}
], function (err, result) {
if(err) {
callback(err);
} else {
callback(null, result);
}
});
}
很遗憾,我无法正确编码。在退出 async.each 之前,我无法从函数中获取结果。有人可以解释一下如何构造代码吗?
调试我发现函数 getAnnotationsFromDocument 获取数据并正确执行最后一个 callback(null, result); ,但是当我到达 function (err,annotations){ ,注释未定义。
【问题讨论】:
-
您能告诉我们
getAnnotationsFromDocument()的代码吗?为什么它甚至不使用doc参数?如果我们能看到该代码,我们可能会向您展示一个更好的方法。 -
另外,为了正确使用
async.each()(现在通常用基于promise的流控制来代替),你需要在你分配@之后将callback(null, annotationsArray)放在前面的回调中987654327@ 在同一个函数中。async.each()不会阻止。它在完成时调用它的回调,因此只有当async.each()告诉你它完成时你才需要调用你的回调。这段带有 3 个回调的代码正是为什么应该将async.each()替换为基于 Promise 的控制流。 -
谢谢@jfriend00。我更改了回调的位置,添加了您要求的功能,并使用更改的结果更新了问题。不幸的是,我仍然收到未定义的注释。
-
如果您希望人们能够理解这里的整个问题并更有可能提供帮助,您将不得不展示所有相关代码,而不仅仅是代码大纲。问题很容易出现在这段代码中的任何地方,其中大部分你没有向我们展示。
标签: javascript node.js each async.js waterfall