如何在没有redis的情况下扩展socket.io

时间:2014-02-06 13:14:17

标签: node.js express socket.io

我正在寻找使用socket.io扩展我的快递应用程序的替代方案。问题是我不想将redis用作socket.io存储。除了使用Clusterhub

之外,还有其他任何可能来集群socket.io 编辑:我尝试使用fakeredis替换redis,但似乎它不适用于socket.io。从ActionHero.js我知道faye-websocket与fakeredis一起使用。

2 个答案:

答案 0 :(得分:2)

这很可能取决于您的socket.io用法和您想要实现的扩展类型(群集与扩展到多台计算机)。

所以,我这样做是为了将socket.io的使用扩展到倍增服务器。

我们在负载均衡器后面有3个服务器,当套接字连接它时连接到3个服务器中的任何一个,三个服务器有一个内存列表的套接字,这三个服务器有一个内部服务器地址的顺序列表,例如: [server1,server2,server3]。

我所做的基本上是一个响铃(在内部我们称之为“套接字响铃”):

  • 如果我需要从server1向套接字发出一个事件,我首先查看套接字是否连接到该server1,如果不是,我将http请求发送到下一个服务器(server2),这将检查套接字是否在那里,如果没有,它会向server3发送相同的请求,依此类推,直到到达原点,在这种情况下你可能会抛出错误。
  • 如果我需要广播消息,它几乎一样,我从一台服务器开始,然后在其他服务器上调用http端点。

我用来确定下一个节点(next_node.js)的算法是:

var nodes = process.env.NODES.split(',');
//this is usually:  http://server1/,http://server2/,http://server3/

var url = require('url');
var current = require("os").hostname();

//origin is the node that started the lookup
exports.get = function (origin) {
  var next_node_i = nodes.map(function (uri) {
    return url.parse(uri).hostname;
  }).reduce(function (prev, curr, i, arr){
    return curr === current && i < arr.length - 1 ? i + 1 : prev;
  }, 0);

  var next_node = nodes[next_node_i];

  if (origin && url.parse(next_node).hostname === origin) {
    // if the next node is equal to the first node initiating the lookup
    // it means the socket we are looking for is not connect to any node.
    return null;
  }

  return next_node;
};

注意事项:

  • 这些服务器和网络分区之间的延迟不太可能,它们实际上位于同一数据中心。但如果是网络分区对我们来说并不重要。
  • 我们总是以相同的方向运行戒指。改进版将在两个方向上运行(?)
  • 服务器共享一个秘密来调用这些端点。

在我看来,这是在很多socket.io用例中实现扩展的一种非常简单的方法,可能还有很多其他场景,这不是一个选项,但我希望这会给出一些想法。

答案 1 :(得分:1)

如果您对Azure服务感到满意,Azure团队中的一些人可以自由地编写service bus store for socket.io

Glenn Block Explains Socket.IO Scale-Out on Service Bus