2

我是 Node.js 的新手,我很好奇规定的方法是在一个进程上(重复地)运行一个循环,在执行结束时,下一步将发生,但只有在所有迭代的回调都有被解雇了。

具体来说,我正在进行 SQL 调用,在进行了一堆插入和更新后,我需要关闭 sql 连接,但是由于它们都是异步的,我无法知道它们实际上何时完成,所以我可以在会话上调用 end()。

显然,这是一个远远超出这个特定示例的问题,所以,我不是在寻找有关 sql 的具体解决方案,而是更多的一般做法,到目前为止,我有点难过。

我现在正在做的实际上是为循环对象的长度设置一个全局计数器,并在每个回调中从它递减以查看它何时达到零,但这感觉真的很笨拙,我希望有一个更优雅的(和以Javascript为中心)的方式来实现这种监控。

TIA

4

2 回答 2

1

有一堆可用的流控制库可以应用模式来帮助处理这种事情。我最喜欢的是异步。例如,如果您想依次运行一堆 SQL 查询,您可以使用series

async.series([
  function(cb) { sql.exec("SOME SQL", cb) },
  function(cb) { sql.exec("SOME MORE SQL", cb) },
  function(cb) { sql.exec("SOME OTHER SQL", cb) }
], function(err, results) {
  // Here, one of two things are true:
  // (1) one of the async functions passed in an error to its callback
  //     so async immediately calls this callback with a non-null "err" value
  // (2) all of the async code is done, and "results" is
  //     an array of each of the results passed to the callbacks
});
于 2012-08-27T20:55:53.800 回答
1

我编写了自己的队列库来做到这一点(我将在这些日子里发布它),基本上将查询推送到队列(基本上是一个数组)上执行每个被删除的查询,当数组为空时发生回调。

不需要太多。

*编辑。我已经添加了这个示例代码。这不是我以前使用过的,也没有在实践中尝试过,但它应该给你一个起点。你可以用这个模式做更多的事情。

需要注意的一件事。排队有效地使您的操作同步,它们一个接一个地发生。我编写了我的 mysql 队列脚本,因此我可以在多个表上异步执行查询,但在任何一个表上同步执行,以便插入和选择按照请求的顺序发生。

var queue = function() {
    this.queue = [];

    /**
     * Allows you to pass a callback to run, which is executed at the end
     * This example uses a pattern where errors are returned from the 
     * functions added to the queue and then are passed to the callback 
     * for handling.
     */
    this.run = function(callback){
        var i = 0;
        var errors = [];

        while (this.queue.length > 0) {
            errors[errors.length] = this.queue[i]();
            delete this.queue[i];
            i++;
        }
        callback(errors);
    }

    this.addToQueue = function(callback){
        this.queue[this.queue.length] = callback;
    }
}

采用:

var q = new queue();
q.addToQueue(function(){
    setTimeout(function(){alert('1');}, 100);
});

q.addToQueue(function(){
    setTimeout(function(){alert('2');}, 50);
});

q.run();
于 2012-08-27T20:59:27.763 回答