等待蓝鸟承诺中的可选流程操作

Waiting for an optional process operation inside bluebird promise

我有一个 bluebird promise, which runs a check. If this check is true, it can continue on. However, if this check is false, it needs to spawn 异步进程,它必须等待完成才能继续。

我有如下内容:

var foo = getPromise();

foo.spread( function (error, stdout, stdin) {
    if (error) {
        // ok, foo needs to hold on until this child exits
        var child = spawn(fixerror);
        child
            .on('error', function (e) {
                //I need to error out here
            })
            .on('close', function (e) {
                //I need to have foo continue here
            });
    } else {
        return "bar";
    }
});

我该怎么做?

首先,为什么您的 .spread() 处理程序将回调与 error 作为第一个参数。这似乎不正确。一个错误应该导致拒绝,而不是完成。

但是,如果这确实是您的代码的工作方式,那么您只需要 return 来自 .spread() 处理程序的承诺。然后该承诺将链接到原始承诺,然后您可以看到两者何时完成:

getPromise().spread( function (error, stdout, stdin) {
    if (error) {
        // ok, foo needs to hold on until this child exits
        return new Promise(function(resolve, reject) {
            var child = spawn(fixerror);
            child.on('error', function (e) {
                //I need to error out here
                reject(e);
            }).on('close', function (e) {
                // plug-in what you want to resolve with here
                resolve(...);
            });
         });
    } else {
        return "bar";
    }
}).then(function(val) {
    // value here
}, function(err) {
    // error here
});

但是,您的 .spread() 处理程序可能不应该在那里有 error 参数,而应该导致拒绝原始承诺:

getPromise().spread( function (stdout, stdin) {
    // ok, foo needs to hold on until this child exits
    return new Promise(function(resolve, reject) {
        var child = spawn(fixerror);
        child.on('error', function (e) {
            //I need to error out here
            reject(e);
        }).on('close', function (e) {
            // plug-in what you want to resolve with here
            resolve(...);
        });
    });
}).then(function(val) {
    // value here
}, function(err) {
    // error here
});

在 promise 函数中包装 spawn 或任何其他替代路由,然后将流程保持为(示例代码):

promiseChain
  .spread((stderr, stdout, stdin) => stderr ? pSpawn(fixError) : 'bar')
  .then(...

// example for promisified spawn code: 
function pSpawn(fixError){
    return new Promise((resolve, reject) => {        
        spawn(fixError)
          .on('error', reject)
          .on('close', resolve.bind(null, 'bar'))        
    })
}