Node.js Promises in Promises 中的嵌套回调中的 Promises 未解析
Node.js Promises in nested callbacks in Promises in Promises not resolving
我有以下无法解析的代码。
f2 解决了,所以我不会添加该代码,我有问题的是 f1。
我调用函数,它到达最里面如果,它调用函数"find",它执行函数findId
,returns Id 完全没问题,然后它执行 editId
但它不解析 document replaced
+ true 我知道它在上下文日志出现时到达。
预期行为:
这应该解决回到最高承诺并达到 context.done()
但它没有
就我在哪里放置新承诺等而言,这可能是一个简单的问题,但我已经为这个结构苦苦挣扎了一段时间。
感谢您的任何见解。
module.exports = function (context, req) {
var documentUrl = xyz;
client.readDocument(documentUrl, (err, a) => {
var f1 = fun1(a,b,c);
var f2 = fun2(a,b,c);
Promise.all([f1, f2]).then(function(results){ //parallel
context.log(results[0], results[1]);
context.done();
});
});
}
function fun1 (a,b,c){
if (a[0].stuff.length > 0) {
var stuffArray = [];
for (i = 0; i < a[0].stuff.length; i++) {
if (a[0].stuff[i].morestuff !== null && a[0].stuff[i].otherstuff !== null) {
if (a[0].stuff[i].Id== null) {
var Id = a[0].id + '_' + i;
var find = findId (a, Id, function(res){
context.log ("findFeedback: found");
context.log(res);
editId(context, res);
});
stuffArray.push(find);
}
} else {
stuffArray.push(i + " shouldn't have Id");
}
}
return Promise.all(stuffArray);
} else {
return ('No stuff');
}
}
function findId(a, Id, callback) {
var documentUrl = myUrl/id;
client.readDocument(documentUrl, (err, result) => {
if (err) {
if (err) {
return(err);
}
} else {
callback(result);
}
});
}
function editId(context, res) {
return new Promise((resolve, reject) => {
var documentUrl = myUrl/res.otherId;
client.readDocument(documentUrl, (err, result) => {
if (err) {
if (err.code == HttpStatusCodes.NOTFOUND) {
context.log('Post does not exist');
resolve('Post does not exist');
} else {
context.log(err);
resolve(err);
}
} else {
context.log('Post exists');
// here i edit some stuff which works fine
client.replaceDocument(documentUrl, result, (err, result) => {
if(err) {
context.log(err);
resolve('Document replaced ' + false);
} else {
context.log('replaced document ' + result);
resolve('Document replaced ' + true);
// This is where my context log ends it does not resolve back up
}
});
}
});
});
};
这里的重点是使您的代码保持一致。
我认为您应该将所有回调函数包装到 Promise。这将使你的代码更干净、更容易,而不是成为意大利面条。
我没有足够的上下文来测试。所以我只是试着稍微重构一下你的代码。希望对你有所帮助。
findId 函数应该 return 一个承诺而不是使用回调:
function findId(Id) {
return new Promise((resolve, reject) => {
var documentUrl = myUrl / id;
client.readDocument(documentUrl, (err, result) => {
if (err) {
reject(err);
} else {
resolve(result);
}
});
});
}
在 fun1 函数中,您在 for 循环中有异步代码。它不会工作,因为异步代码不会等到它为您提供结果。所以我通过将你需要调用 findId
的 id 推送到 stuffArr
来重构。然后,我将这些 id 映射到 promise 函数列表 findId
。通过这样做,我们可以使用 Promise.all 等待所有的承诺处理。
function fun1(a, b, c) {
if (a[0].stuff.length > 0) {
var stuffArray = [];
for (i = 0; i < a[0].stuff.length; i++) {
if (
a[0].stuff[i].morestuff !== null &&
a[0].stuff[i].otherstuff !== null
) {
if (a[0].stuff[i].Id == null) {
var Id = a[0].id + "_" + i;
var promise = findId(Id)
.then(res => editId(context, res))
.catch(err => i + " Some error");
stuffArray.push(promise);
} else {
// don't know what you want to do here
}
} else {
stuffArray.push(i + " shouldn't have Id");
}
}
return Promise.all(stuffFindPromises);
} else {
return Promise.resolve("No stuff");
}
}
希望这对您有所帮助。
findId
需要 return new Promise((resolve,reject) => { });
环绕它。
然后您可以在 findId
内调用 editId
并将 callback(result)
替换为 resolve(editId(context, result));
之后将 fun1
中的 var find
替换为 var find = findId (a, id)
并删除 findId
中的回调要求
我有以下无法解析的代码。 f2 解决了,所以我不会添加该代码,我有问题的是 f1。
我调用函数,它到达最里面如果,它调用函数"find",它执行函数findId
,returns Id 完全没问题,然后它执行 editId
但它不解析 document replaced
+ true 我知道它在上下文日志出现时到达。
预期行为:
这应该解决回到最高承诺并达到 context.done()
但它没有
就我在哪里放置新承诺等而言,这可能是一个简单的问题,但我已经为这个结构苦苦挣扎了一段时间。
感谢您的任何见解。
module.exports = function (context, req) {
var documentUrl = xyz;
client.readDocument(documentUrl, (err, a) => {
var f1 = fun1(a,b,c);
var f2 = fun2(a,b,c);
Promise.all([f1, f2]).then(function(results){ //parallel
context.log(results[0], results[1]);
context.done();
});
});
}
function fun1 (a,b,c){
if (a[0].stuff.length > 0) {
var stuffArray = [];
for (i = 0; i < a[0].stuff.length; i++) {
if (a[0].stuff[i].morestuff !== null && a[0].stuff[i].otherstuff !== null) {
if (a[0].stuff[i].Id== null) {
var Id = a[0].id + '_' + i;
var find = findId (a, Id, function(res){
context.log ("findFeedback: found");
context.log(res);
editId(context, res);
});
stuffArray.push(find);
}
} else {
stuffArray.push(i + " shouldn't have Id");
}
}
return Promise.all(stuffArray);
} else {
return ('No stuff');
}
}
function findId(a, Id, callback) {
var documentUrl = myUrl/id;
client.readDocument(documentUrl, (err, result) => {
if (err) {
if (err) {
return(err);
}
} else {
callback(result);
}
});
}
function editId(context, res) {
return new Promise((resolve, reject) => {
var documentUrl = myUrl/res.otherId;
client.readDocument(documentUrl, (err, result) => {
if (err) {
if (err.code == HttpStatusCodes.NOTFOUND) {
context.log('Post does not exist');
resolve('Post does not exist');
} else {
context.log(err);
resolve(err);
}
} else {
context.log('Post exists');
// here i edit some stuff which works fine
client.replaceDocument(documentUrl, result, (err, result) => {
if(err) {
context.log(err);
resolve('Document replaced ' + false);
} else {
context.log('replaced document ' + result);
resolve('Document replaced ' + true);
// This is where my context log ends it does not resolve back up
}
});
}
});
});
};
这里的重点是使您的代码保持一致。
我认为您应该将所有回调函数包装到 Promise。这将使你的代码更干净、更容易,而不是成为意大利面条。
我没有足够的上下文来测试。所以我只是试着稍微重构一下你的代码。希望对你有所帮助。
findId 函数应该 return 一个承诺而不是使用回调:
function findId(Id) {
return new Promise((resolve, reject) => {
var documentUrl = myUrl / id;
client.readDocument(documentUrl, (err, result) => {
if (err) {
reject(err);
} else {
resolve(result);
}
});
});
}
在 fun1 函数中,您在 for 循环中有异步代码。它不会工作,因为异步代码不会等到它为您提供结果。所以我通过将你需要调用 findId
的 id 推送到 stuffArr
来重构。然后,我将这些 id 映射到 promise 函数列表 findId
。通过这样做,我们可以使用 Promise.all 等待所有的承诺处理。
function fun1(a, b, c) {
if (a[0].stuff.length > 0) {
var stuffArray = [];
for (i = 0; i < a[0].stuff.length; i++) {
if (
a[0].stuff[i].morestuff !== null &&
a[0].stuff[i].otherstuff !== null
) {
if (a[0].stuff[i].Id == null) {
var Id = a[0].id + "_" + i;
var promise = findId(Id)
.then(res => editId(context, res))
.catch(err => i + " Some error");
stuffArray.push(promise);
} else {
// don't know what you want to do here
}
} else {
stuffArray.push(i + " shouldn't have Id");
}
}
return Promise.all(stuffFindPromises);
} else {
return Promise.resolve("No stuff");
}
}
希望这对您有所帮助。
findId
需要 return new Promise((resolve,reject) => { });
环绕它。
然后您可以在 findId
内调用 editId
并将 callback(result)
替换为 resolve(editId(context, result));
之后将 fun1
中的 var find
替换为 var find = findId (a, id)
并删除 findId