Nodejs在每个瀑布里面都是异步的

时间:2017-11-16 07:05:14

标签: node.js async.js

我一直在用这种方式敲打我的头。也许这里有人可以帮助我一点?

我有一个包含对象数组的对象,我需要在继续之前依次对每个对象进行一些操作。这是一个简单的例子,是我一直在尝试的众多例子之一:

    var demo = {
        one: ['1'],
        two: ['2'],
        three: ['3', '4', '5']
    };

    async.waterfall([
        function(callback) {
            console.log("Step 1");
            setTimeout(function() {
                    console.log("Doing stuff...");
                    callback(null, demo);
            }, 1000);
        },
        function(prevData, callback) {
            console.log("Step 2");
            async.each(prevData, function(obj) {
                async.each(obj, function(item, callback2) {
                    setTimeout(function() {
                            console.log("Doing stuff for item: "+item);
                            callback2(null, demo);
                    }, 1000);
                });
            });
            callback(null, demo);
        }
    ], function(err) {
        if(err) {
            alertify.error("Unhandled exception: "+err);
        } else {
            console.log("All stuff done.");
        }
    });

我期待的是:

Step 1
Doing stuff...
Step 2
Doing stuff for item: 1
Doing stuff for item: 2
Doing stuff for item: 3
Doing stuff for item: 4
Doing stuff for item: 5
All stuff done.

但我得到的是:

Step 1
Doing stuff...
Step 2
All stuff done.
Doing stuff for item: 1
Doing stuff for item: 2
Doing stuff for item: 3
Doing stuff for item: 4
Doing stuff for item: 5

如果尝试过,可能是我能想到的每个级别的回调组合,除了正确的组合。一定是显而易见但我只是不明白......

序列本身是正确的,但是应该操作项目的函数在以后才会执行。

1 个答案:

答案 0 :(得分:0)

问题出在这一部分:

    function(prevData, callback) {
        console.log("Step 2");
        async.each(prevData, function(obj) {
            async.each(obj, function(item, callback2) {
                setTimeout(function() {
                        console.log("Doing stuff for item: "+item);
                        callback2(null, demo);
                }, 1000);
            });
        });
        callback(null, demo);
    }

async.each之后,您立即致电callback(null, demo);。这是在async.each完成之前。只有在async.each完成后才需要调用callback。你通过添加另一个回调作为async.each的第三个参数来实现这一点,如下所示:

function (prevData, callback) {
    console.log("Step 2");
    async.each(prevData, function (obj) {
        async.each(obj, function (item, callback2) {
            setTimeout(function () {
                console.log("Doing stuff for item: " + item);
                callback2(null, demo);
            }, 1000);
        });
    }, function asyncEachDone(err) {
        callback(err, prevData)
    })
}