无极瀑布

Promise waterfall

我是一名 API 开发人员,通常会编写端点,要求将一个异步调用的结果传递给另一个异步调用,也就是异步瀑布。

我通常使用 promises 通过以下方式执行此操作:

task1()

.then(result1){

    task2(result1)

    .then(result2){

        task3(result2)

        .then(result3){
            // API response
        })

        .catch(function(err){
            // Task 3 handle err
        })
    })

    .catch(function(err){
        // Task 2 handle err
    })
})

.catch(function(err){
    // Task 1 handle err
})

很明显,使用回调并没有带来太多好处。而不是 "callback hell" 我现在得到 "promise hell".

我看过npm bluebird,但似乎不支持瀑布承诺。

有时我会使用 async 并包装 return 承诺的任务:

const tasks = [

    job1: function(cb){

        task1()

        .then(function(result){
            cb(null, result);
        })

        .catch(function(err){
            cb(err);
        })  
    },

    job2: function(cb, result1){

        task2(result1)

        .then(function(result){
            cb(null, result);
        })

        .catch(function(err){
            cb(err);
        })  
    },

    job3: function(cb, result2){

        task3(result2)

        .then(function(result){
            cb(null, result);
        })

        .catch(function(err){
            cb(err);
        })  
    }
]

async.series(tasks, function(err, results){

    if(err){
        // handle error
    }

    // API callback
});

但这也没什么用。 而且,如果您正在考虑 Promise.all,那是行不通的,因为一个任务的结果不会传递给下一个任务。

更好的方法是什么?

你有一个承诺反模式正在发生。您可以 return 从承诺中承诺,以避免像您所做的那样嵌套承诺。

promiseOne()
    .then(() => promiseTwo())
    .then(() => promiseThree())
    .then(() => promiseFour());

顺便说一句,Node 支持内置的 Promise 构造函数。

https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise

const promise = new Promise((resolve, reject) => {
    // do something and then resolve
    resolve();
})
promise().then(() => { ... });