相关疑难解决方法(0)

Node.js,Socket.io,Redis pub/sub高容量,低延迟的困难

当连接socket.io/node.js和redis pub/sub以尝试创建由可处理多个传输的服务器事件驱动的实时Web广播系统时,似乎有三种方法:

  1. 'createClient'是一个redis连接并订阅了频道.在socket.io客户端连接上,将客户端加入socket.io会议室.在redis.on("message",...)事件中,调用io.sockets.in(room).emit("event",data)以分发给相关房间中的所有客户端.喜欢如何在socket.io中重用redis连接?

  2. 'createClient'是一个redis连接.在socket.io客户端连接上,将客户端加入socket.io会议室并订阅相关的redis频道.在客户端连接闭包内和收到消息调用client.emit("event",data)时包含redis.on("message",...)以在特定客户端上引发事件.就像在socket.io中使用RedisStore的示例中的答案一样

  3. 使用RedisStore烘焙到socket.io和'广播'从Redis中的单个"调度"通道遵循socketio-spec协议.

Number 1允许为所有客户端处理一次Redis子和相关事件.Number 2为Redis pub/sub提供了更直接的钩子.3号更简单,但几乎无法控制消息传递事件.

但是,在我的测试中,所有连接的客户端都表现出意外的低性能.有问题的服务器事件是尽快发布到redis频道的1,000条消息,以便尽快分发.性能是通过连接客户端的时间来衡量的(socket.io-client基于该日志时间戳到Redis列表中进行分析).

我猜测在选项1中,服务器接收消息,然后顺序将其写入所有连接的客户端.在选项2中,服务器多次接收每个消息(每个客户端订阅一次)并将其写入相关客户端.在任何一种情况下,服务器都不会进入第二个消息事件,直到它被传递给所有连接的客户端.随着并发性的上升,情况显然更加恶化.

这似乎与堆栈功能的感知智慧不一致.我想相信,但我在苦苦挣扎.

这种情况(大量消息的低延迟分布)是不是这些工具的选项(但是?),还是我错过了一个技巧?

publish-subscribe redis low-latency node.js socket.io

65
推荐指数
1
解决办法
3万
查看次数

我该怎么用?Socket.io房间还是Redis pub-sub?

非常简单的问题.我正在使用nodejs作为我的后端构建一个实时游戏,我想知道是否有任何信息可用哪个更可靠哪个更有效?我在整个代码中大量使用Redis和Socket.io.所以我想知道我是否应该使用Socket.io的房间,或者我最好使用redis'pub -sub

更新: 刚刚意识到有一个非常重要的原因,你可能想在socket.io房间使用redis pub/sub.使用Socket.io房间发布给监听器时,(浏览器)客户端收到消息,redis实际上是(redis~on on server)客户端收到消息.因此,如果您想要通知所有(服务器)客户端特定于每个客户端的信息,并且可能在传递给浏览器客户端之前进行一些处理,那么最好使用redis.使用redis你可以发起一个事件来生成每个用户的个人数据,就像socket.io一样,你必须一次实际生成所有用户的唯一数据,然后遍历它们并发送它们各自的数据,这几乎击败了房间的目的,至少对我而言.

不幸的是,就我的目的而言,我现在仍然坚持使用redis.

更新2:结束开发插件只使用2个redis连接,但仍然允许单独的客户端处理,请参阅下面的答案....

publish-subscribe redis node.js socket.io

29
推荐指数
2
解决办法
2万
查看次数

如何删除'message'侦听器上的Redis

一个典型的Redis聊天示例将是这样的(请参阅https://github.com/emrahayanoglu/Socket.io-Redis-RealTime-Chat-Example/blob/master/chatServer.js仅用于一个这样的示例):

io.sockets.on('connection', function (client) { //websocket connection

  redis1.subscribe("chat");

  redis1.on("message", function(channel, message) {
      console.log(message);
      client.send(message);
  });

  client.on('message', function(msg) {
    redis2.publish("chat",msg.message);  
  });

  client.on('disconnect', function() {
      redis1.quit();
  });
});
Run Code Online (Sandbox Code Playgroud)

但是,这里的问题是当client"断开"时,redis1.on('message',FUNC(){})监听器仍然连接.控制台将继续打印出来message.如果要检查事件列表的人redis1,他们仍会发现匿名函数正在侦听.

问题是没有任何redis1.off(...)功能.那么,如何取消绑定/取消订阅/删除/删除redis消息监听器?

注意:不能只执行redis1.end(),因为这会破坏其他websocket连接用户的redis连接.

publish-subscribe websocket redis node.js

17
推荐指数
1
解决办法
5927
查看次数

nodeJS中的发布/订阅实现

我一直在玩nodeJS的不同发布/订阅实现,并且想知道哪一个最适合特定的应用程序.该应用程序的要求涉及在多通道,多用户3D环境中实时同步对象.

我开始使用socket.io,创建了一个基本的通道数组,当用户发送消息时,它会循环通过该通道中的用户并向用户的客户端发送消息.这很好用,我没有遇到任何问题.

对于对象持久性,我使用node_redis添加了Redis支持.然后我用Redis pub/sub替换了通道数组上的client.send循环作为抽象层.但我注意到我需要为每个订阅用户创建一个新的Redis客户端.而且我仍然需要存储socket.io客户端信息以便在发布时发送消息.这有多可扩展?是否有其他(更好的)实现或进一步优化?你会怎么做?

javascript publish-subscribe redis node.js

13
推荐指数
1
解决办法
9122
查看次数

节点:缩放socket.io/nowjs - 跨不同实例进行缩放

在开始编写我的应用程序之前,我需要知道当单个node.js实例(express和(socket.io或nowjs))不再足够时该怎么做.

你现在可能告诉我,我不应该关心规模直到时间,但我不想开发应用程序并遇到麻烦,因为你不能轻易地在多个实例中扩展socket.io或nowjs.

我最近读到socket.io现在支持使用Redis进行扩展的方法(我也没有经验).Nowjs是基于socket.io构建的 - 它的工作方式是否相同?在nowjs.org上,您可以读到"NowJS的分布式版本"正在开发中,并且需要花钱.

node.js socket.io nowjs-sockets

11
推荐指数
1
解决办法
4947
查看次数

Node.js,多线程和Socket.io

我希望让Socket.io 在Node.js v.0.6.0及更高版本中使用本机负载平衡("集群")进行多线程.

据我所知,Socket.io使用Redis来存储其内部数据.我的理解是:我们不想为每个工作者生成一个新的Redis实例,而是强制工作者使用与主服务器相同的Redis实例.因此,连接数据将在所有工作人员之间共享.

在主人中有类似的东西:

RedisInstance = new io.RedisStore;
Run Code Online (Sandbox Code Playgroud)

我们必须以某种方式传递RedisInstance给工人并做以下事情:

io.set('store', RedisInstance);
Run Code Online (Sandbox Code Playgroud)

受到使用旧的第三方集群模块的此实现的启发,我有以下非工作实现:

var cluster = require('cluster');
var http = require('http');
var numCPUs = require('os').cpus().length;

if (cluster.isMaster) {
  // Fork workers.
  for (var i = 0; i < numCPUs; i++) {
    cluster.fork();
  }

  var sio = require('socket.io')
  , RedisStore = sio.RedisStore
  , io = sio.listen(8080, options);

  // Somehow pass this information to the workers
  io.set('store', new RedisStore);

} else {
  // Do the work …
Run Code Online (Sandbox Code Playgroud)

javascript node.js socket.io

10
推荐指数
1
解决办法
1万
查看次数

您是否应该打开Redis,或者在节点中每次使用后打开并退出?

我有一个使用redis的socket.io服务器,名为"server.js",用于启动节点服务器.目前它是这样的:

var client = redis.createClient()
var io = require('socket.io').listen(80);

io.sockets.on('connection', function (socket) {
  client.set(); // do something with redis
});
Run Code Online (Sandbox Code Playgroud)

然后我启动我的服务器,它只是保持活着.这是错的吗?应该是这样吗?

var io = require('socket.io').listen(80);

io.sockets.on('connection', function (socket) {
  var client = redis.createClient()
  client.set(); // do something with redis
  client.quit();
});
Run Code Online (Sandbox Code Playgroud)

我应该继续打开和关闭redis,还是我可以打开它一次然后打开它?以上哪个片段是启动服务器的正确方法?

redis node.js socket.io

8
推荐指数
1
解决办法
3944
查看次数

Redis和Node.js以及Socket.io问题

我一直在学习redis和node.js我有两个问题,我找不到任何令人满意的答案.

我的第一个问题是在node.js中重用redis客户端.我找到了这个问题并回答:如何在socket.io中重用redis连接?,但它并不能让我满意.

现在,如果我在连接事件中创建redis客户端,它将为每个连接生成.因此,如果我有20k并发用户,那么将有20k redis客户端.

如果我把它放在连接事件之外,它只会产生一次.

答案是说他在连接事件之外为每个函数创建了三个客户端.

但是,据我所知,MySQL在编写生成子进程并并行运行的应用程序时,需要在创建子实例的函数中创建MySQL客户端.如果你在它之外创建它,MySQL将给出"MySQL服务器已经消失"的错误,因为子进程将尝试使用相同的连接.应该分别为每个子进程创建它.

因此,即使您为每个函数创建了三个不同的redis客户端,如果您有30k并发用户同时发送2k个消息,那么您应该遇到同样的问题,对吧?因此,每个"用户"都应该在连接事件中拥有自己的redis客户端.我对吗?如果没有,node.js或redis如何处理并发请求,与MySQL不同?如果它有自己的机制并在redis客户端中创建类似子进程的东西,为什么我们需要创建三个不同的redis客户端呢?一个应该就够了.

我希望这个问题很明确.

- 更新 -

我找到了以下问题的答案.http://howtonode.org/control-flow 无需回答,但我的第一个问题仍然有效.

- 更新 -

我的第二个问题是这个.我在JS和Node.js上也不是那么擅长.所以,据我所知,如果你需要等待一个事件,你需要在第一个函数中封装第二个函数.(我还不知道术语).让我举个例子;

socket.on('startGame', function() {
    getUser();
    socket.get('game', function (gameErr, gameId) {
        socket.get('channel', function (channelErr, channel) {
            console.log(user);
            client.get('games:' + channel + '::' + gameId + ':owner', function (err, owner) { //games:channel.32:game.14
                if(owner === user.uid) {
   //do something
                }
            });
        }
    });
});
Run Code Online (Sandbox Code Playgroud)

所以,如果我正确学习它,我需要运行函数中的每个函数,如果我需要等待I/O答案.否则,node.js的非阻塞机制将允许第一个函数运行,在这种情况下,它将并行获得结果,但如果需要时间,第二个函数可能没有结果.因此,如果您从redis获得结果,并且您将在第二个函数中使用结果,则必须将其封装在redis get函数中.否则第二个函数将运行而不会得到结果.

所以,在这种情况下,如果我需要运行7个不同的函数,而8.函数将需要所有函数的结果,我是否需要递归地这样写它们?或者我错过了什么.

我希望这也很清楚.

非常感谢,

redis node.js

6
推荐指数
1
解决办法
2296
查看次数

将socket.io与Cluster一起使用?

我很好奇我可以同时使用socket.io和Cluster.

我知道集群使用多核来处理具有多个worker的node.js.

这意味着如果我使用cluster for socket.io,两个用户连接

两个不同的socket.io可能会导致他们无法相互通信的问题?

所以不是在socket.io上使用集群会是一个答案吗?

cluster-computing node.js socket.io

5
推荐指数
1
解决办法
5079
查看次数

如何让不同的Web浏览器在Redis/Node.js/Socket.io pub/sub设置中订阅单独的频道?

我希望不同的客户端(Web浏览器)能够订阅单独的Redis频道.

我能够将请求的通道从客户端页面传递到node.js服务器.但是,如果我有三个浏览器订阅,每个订阅三个单独的频道,所有三个浏览器接收发布到三个频道中的任何一个的消息.

这是客户端HTML代码.我有三个单独的页面,其中频道名称是硬编码的.在此示例中,通道为"channel1".

client1.html

<script src="/socket.io/socket.io.js"></script>
<script>
var socket = io.connect('http://localhost');
socket.on('giveChannel', function () {
    console.log('sending channel');
    socket.emit('sendChannel', "{\"channel\":\"channel\"}");
});

socket.on('message', function (data) {
    console.log(data);
});
</script>
Run Code Online (Sandbox Code Playgroud)

这是Node.js文件.

app.js

redis = require('redis'),
sys = require('sys');
var http = require('http');
var url = require('url');
var fs = require('fs');

var server = http.createServer(function (req, res) {
    var path = url.parse(req.url).pathname;
    fs.readFile(__dirname + path, function(err, data) {
        if (err) return null;
        res.writeHead(200, {'Content-Type': 'text/html'});
        res.write(data, 'utf8');
        res.end();
    });

});

io = require('socket.io').listen(server);

io.sockets.on('connection', …
Run Code Online (Sandbox Code Playgroud)

javascript publish-subscribe redis node.js socket.io

3
推荐指数
1
解决办法
2186
查看次数

在不同的节点进程之间实现pubsub

我正在编写基于nodejs的rest API.

我的API有不同的方法,比如put/friends将用户添加到当前登录用户的朋友列表中.

我想通过不同的方法(推送通知,邮件等)通知其他用户,他已被添加为朋友.我不想在API流程中进行通知,而是想发布另一个nodejs处理的事件(可能甚至在不同的机器上运行),拾取并执行通知工作.

实现此类架构的可接受方法有哪些?这里的关键是我想要不同的 nodejs进程之间的pub/sub模式甚至可能不共享同一台机器,所以我想常规的EventEmitter不会帮助那里.

感谢帮助!

publish-subscribe node.js

0
推荐指数
1
解决办法
819
查看次数