分布式信号量系统,用于序列化不能同时运行的任务

时间:2012-04-28 19:00:31

标签: node.js mongodb redis rabbitmq zeromq

我正在寻找一种方法来序列化影响数据存储中数据的任务,而不使用 MySQL 例如: 在group1上进行会计处理的工作人员应该是唯一一个在第一组进行会计处理的工作人员,如果另一个工作人员在第一组进行会计核算,则应该排队等候。

我可以通过设置信号量表,启动事务,对group1行执行更新,执行任务和提交来完成此操作。

我在想,也许可以使用0mq redis或某种消息传递系统来实现相同的目标,并允许我使用我想要的数据存储。 我还认为 ScalienDB 可能能够在与mysql相同的庄园中解决问题,因为它看到它支持事务。 ScalienDB 的文档似乎有些不完整,所以我无法确定它是否可以以这种方式进行交易。
所以我的问题是:

  1. ScalienDB 可以执行一个事务,如果它想要编辑另一个客户端也对其进行编辑的表中的行,则会强制客户端等待另一个客户端提交。

  2. 使用消息传递系统,您如何建议实现可归结为以下内容的内容:

  3. var semaphore = semaphore_group()
    semaphore.acquire('task1',function(){
        // do work after a sophomore is locked in
        semaphore.release() //
    })
    

    理想情况下,我不希望这个系统依赖于集中式代理

    1. 是否有适合此问题的替代解决方案

2 个答案:

答案 0 :(得分:1)

我最喜欢Node的是 no-threads ,这意味着每行代码都可以被视为 atomic 。因此,您可以轻松编写几行JS代码,这些代码将运行一个套接字服务器,为工作人员提供您希望拥有的机制,如示例代码中所示。

我不确定在技术上是否正确调用此信号量,因为我们会跟踪等待转弯的工人。

工:

var Semaphore = reqire('./semaphore.js'),
    semaphore = new Semaphore(worker-id, group-id);

semaphore.on('ready', function() {
    // Yay! We can work..!
    semaphore.done();
}

semaphore.js骨架:

// imports...

module.exports = S = function(gid) {
    events.EventEmitter.call(this);

    // create socket connection to semaphore server
    // send a message for lock on gid
    // emit ready event when server sends ready message.
    // send 'done' message when done() method is called.

}; util.inherits(S, events.EventEmitter);

semaphore-server.js skeleton:

// imports...

var queues = {};  // { 'group-id': [worker1, worker2, ...] }

// start socket server

/* on message: take worker-id and group-id
   queues[groupid].push(workerid);
   check if queues[groupid][0]==workerid and if it is,
   send back ready message.
*/

/* on message 'done', remove workerid from queues[groupid]
   and if there are any workers waiting, send the first one
   ready message.
*/

您的代码不会比上面的骨架长得多。对于这种简单的消息传递系统,ZeroMQ或任何其他消息传递不是必需的。您可以考虑向工作人员添加超时,并且每当发生超时时,向工作人员发送消息,询问“您还在工作吗?”并继续根据。您的超时处理程序还可以检查队列中是否有其他工作人员,如果没有,则甚至不需要打扰工作人员......

我通常更喜欢使用手头已经拥有的工具,而不是去第三方,如果我需要的只是一个简单的系统,我可以在这样的一小时内构建。任何其他库/ dbms / messaing系统或任何其他会增加我不喜欢的软件的复杂性和管理苦差事。既然你已经在Node中构建了一些东西,它已经完美地提供了你想要的东西,我相信这是要走的路。

答案 1 :(得分:0)

我会考虑使用像Apache Zookeeper这样的分布式协调服务来创建和处理分布式锁。这是一个描述你如何去做的食谱:http://zookeeper.apache.org/doc/trunk/recipes.html#sc_recipes_Locks