首页 > 解决方案 > Node.js Promises in Promises in Promises 嵌套回调中的 Promise 未解决

问题描述

我有以下无法解析的代码。f2 解决了,所以我不会添加该代码,这是 f1 我有问题。

我调用该函数并且它到达最里面如果,它调用函数“find”,该函数执行函数findId,返回 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 
                }
        });                

             }
        });
    });
};

标签: javascriptnode.jspromiseresolve

解决方案


这里的重点是使您的代码保持一致。

我认为您应该将所有回调函数包装到 Promise。这将使您的代码更清洁、更容易,而不是成为意大利面条。

我没有足够的上下文来测试。因此,我只是尝试稍微重构您的代码。希望它在某些方面对您有所帮助。

findId 函数应该返回一个 promise 而不是使用回调:

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 循环中有异步代码。它不起作用,因为异步代码不会等到它为您提供结果。所以我通过推送你需要调用的 id 来findId重构stuffArr. 然后,我将这些 id 映射到 promise function 列表中findId。通过这样做,我们可以使用 Promise.all 来等待所有的 Promise 处理完毕。

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");
  }
}

希望这可以帮助。


推荐阅读