通过Socket.io使用Redis作为PubSub

我正在创build一个聊天应用程序,使用户可以进行私人聊天和群聊。 计划使用此应用程序的以下技术: –

NodeJs + Socket.io + Redis + CouchDB(用于存储消息历史logging)+ AngularJS

根据我最初的研究,使用Redis作为PubSub服务是比使用Socket.io作为pub-sub更好的方法。原因在于,如果不同的用户连接到不同的服务器实例,那么在这种情况下使用套接字将会产生问题,用户1不会传递给用户2(用户1连接到服务器1,用户2连接到服务器2)。

但是,如果我们使用Redis,那么根据我的理解,我们必须创build新的渠道来实现私人聊天。 而且它们是Redis中10k频道的限制。

我的疑问是

  1. 我是否需要每次创build新频道以启用两个用户之间的私密聊天?
  2. 如果我需要创build单独的频道,那么实际上是否有10K频道的限制?
  3. 我需要一个使用Redis作为pub / sub与socket.io启用私人聊天的工作示例。

问候,Vikram

在阅读下面的文章/博客文章后,使用Redis for pub / sub over socket.io pub / sub将有助于扩展性和更好的性能。

https://github.com/sayar/RedisMVA/blob/master/module6_redis_pubsub/README.md

https://github.com/rajaraodv/redispubsub

此外,我可以使用redis创build一个私人聊天的快速POC。 这是代码: –

var app = require('http').createServer(handler); app.listen(8088); var io = require('socket.io').listen(app); var redis = require('redis'); var redis2 = require('socket.io-redis'); io.adapter(redis2({ host: 'localhost', port: 6379 })); var fs = require('fs'); function handler(req,res){ fs.readFile(__dirname + '/index.html', function(err,data){ if(err){ res.writeHead(500); return res.end('Error loading index.html'); } res.writeHead(200); console.log("Listening on port 8088"); res.end(data); }); } var store = redis.createClient(); var pub = redis.createClient(); var sub = redis.createClient(); sub.on("message", function (channel, data) { data = JSON.parse(data); console.log("Inside Redis_Sub: data from channel " + channel + ": " + (data.sendType)); if (parseInt("sendToSelf".localeCompare(data.sendType)) === 0) { io.emit(data.method, data.data); }else if (parseInt("sendToAllConnectedClients".localeCompare(data.sendType)) === 0) { io.sockets.emit(data.method, data.data); }else if (parseInt("sendToAllClientsInRoom".localeCompare(data.sendType)) === 0) { io.sockets.in(channel).emit(data.method, data.data); } }); io.sockets.on('connection', function (socket) { sub.on("subscribe", function(channel, count) { console.log("Subscribed to " + channel + ". Now subscribed to " + count + " channel(s)."); }); socket.on("setUsername", function (data) { console.log("Got 'setUsername' from client, " + JSON.stringify(data)); var reply = JSON.stringify({ method: 'message', sendType: 'sendToSelf', data: "You are now online" }); }); socket.on("createRoom", function (data) { console.log("Got 'createRoom' from client , " + JSON.stringify(data)); sub.subscribe(data.room); socket.join(data.room); var reply = JSON.stringify({ method: 'message', sendType: 'sendToSelf', data: "Share this room name with others to Join:" + data.room }); pub.publish(data.room,reply); }); socket.on("joinRooom", function (data) { console.log("Got 'joinRooom' from client , " + JSON.stringify(data)); sub.subscribe(data.room); socket.join(data.room); }); socket.on("sendMessage", function (data) { console.log("Got 'sendMessage' from client , " + JSON.stringify(data)); var reply = JSON.stringify({ method: 'message', sendType: 'sendToAllClientsInRoom', data: data.user + ":" + data.msg }); pub.publish(data.room,reply); }); socket.on('disconnect', function () { sub.quit(); pub.publish("chatting","User is disconnected :" + socket.id); }); }); 

HTML代码

 <html> <head> <title>Socket and Redis in Node.js</title> <script src="/socket.io/socket.io.js"></script> <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.6.4/jquery.min.js"></script> </head> <body> <div id="username"> <input type="text" name="usernameTxt" /> <input type="button" name="setUsername" value="Set Username" /> </div> <div id="createroom" style="display:none;">> <input type="text" name="roomNameTxt" /> <input type="button" name="setRooomName" value="Set Room Name" /> <input type="button" name="joinRooomName" value="Join" /> </div> <div id="sendChat" style="display:none;"> <input type="text" name="chatTxt" /> <input type="button" name="sendBtn" value="Send" /> </div> <br /> <div id="content"></div> <script> $(document).ready(function() { var username = "anonymous"; var roomname = "anonymous"; $('input[name=setUsername]').click(function(){ if($('input[name=usernameTxt]').val() != ""){ username = $('input[name=usernameTxt]').val(); //var msg = {type:'setUsername',user:username}; socket.emit('setUsername',{user:username}); } $('#username').slideUp("slow",function(){ $('#createroom').slideDown("slow"); }); }); $('input[name=setRooomName]').click(function(){ if($('input[name=roomNameTxt]').val() != ""){ roomname = $('input[name=roomNameTxt]').val(); socket.emit('createRoom',{user:username,room:roomname}); } $('#createroom').slideUp("slow",function(){ $('#sendChat').slideDown("slow"); }); }); $('input[name=joinRooomName]').click(function(){ if($('input[name=roomNameTxt]').val() != ""){ roomname = $('input[name=roomNameTxt]').val(); socket.emit('joinRooom',{room:roomname}); } $('#createroom').slideUp("slow",function(){ $('#sendChat').slideDown("slow"); }); }); var socket = new io.connect('http://localhost:8088'); var content = $('#content'); socket.on('connect', function() { console.log("Connected"); }); socket.on('message', function(message){ //alert('received msg=' + message); content.append(message + '<br />'); }) ; socket.on('disconnect', function() { console.log('disconnected'); content.html("<b>Disconnected!</b>"); }); $("input[name=sendBtn]").click(function(){ var msg = {user:username,room:roomname,msg:$("input[name=chatTxt]").val()} socket.emit('sendMessage',msg); $("input[name=chatTxt]").val(""); }); }); </script> </body> </html> 

这是所有代码基本的redis pub / sub。

 var redis = require("redis"); var pub = redis.createClient(); var sub = redis.createClient(); sub.on("subscribe", function(channel, count) { console.log("Subscribed to " + channel + ". Now subscribed to " + count + " channel(s)."); }); sub.on("message", function(channel, message) { console.log("Message from channel " + channel + ": " + message); }); sub.subscribe("tungns"); setInterval(function() { var no = Math.floor(Math.random() * 100); pub.publish('tungns', 'Generated Chat random no ' + no); }, 5000); 

如果你需要弄湿脚步并创build一个简单的聊天应用程序,那么下面的开发堆栈可以很好地协同工作:

  • Express.js(Node.js)
  • Redis的
  • Socket.IO

该应用程序由用户可以join并启动对话的聊天室组成。 当聊天计数/消息更新时,Socket.IO负责发送事件,并使用jQuery在UI中刷新这些事件。

有关完整的文章和源代码,请查看以下链接: https : //scalegrid.io/blog/using-redis-with-node-js-and-socket-io/