[REDIS] 어떻게 사용되어야 하는가? Socket.io 객실 또는 레디 스 펍 서브?
REDIS어떻게 사용되어야 하는가? Socket.io 객실 또는 레디 스 펍 서브?
아주 간단한 질문입니다. 내 백엔드로 nodejs를 사용하여 실시간으로 게임을 구축하고 거기에 어떤 정보가 하나 더 신뢰할 수있는 가능하며, 하나가 더 효율적이다 궁금 무엇입니까? 나는 주로 내 코드에 걸쳐있는 레디 스 및 Socket.io를 사용하고 있습니다. 나는 Socket.io의 객실을 활용해야한다 또는 내가 레디 스 '술집 서브를 사용하여 더 나을 것입니다 여부를 알고 싶어 그래서?
최신 정보: 그냥 당신이 socket.io 객실에 걸쳐 레디 스 펍 / 하위를 사용할 수 있습니다 이유는 매우 중요한 이유가 깨달았다. Socket.io 객실 사용하면 (브라우저) 클라이언트는 실제로 메시지를받을 (서버 레디 스 ~) 클라이언트입니다 레디 스에 메시지를받을, 청취자에 게시 할 때. 각 클라이언트에 정보를 특정의 모든 (서버) 클라이언트를 통보하고 어쩌면 브라우저 클라이언트에 전달하기 전에 일부 처리를 수행하려는 경우 따라서, 당신은 더 나은 레디 스를 개시한다. 레디 스를 사용하여 당신은 각 사용자 개별 데이터를 생성하는 이벤트를 해고 할 수있는 당신이 실제로 그들을 통해 모든 사용자에게 한 번에 고유 한 데이터, 다음 루프를 생성하고 그들에게 거의 패배 개별 데이터를 전송해야 Socket.IO에와 같이 객실의 목적, 나를 위해 적어도.
불행하게도 나의 목적을 위해 나는 지금 레디 스에 붙어있다.
업데이트 2 : .... 플러그인 만 2 레디 스 연결을 사용하지만 여전히 개별 클라이언트 처리를 허용, 아래의 답을보고 개발까지 종료
해결법
-
==============================
1.레디 스 펍 / 서브 경우 모든 클라이언트가 레디 스에 직접 액세스 할 중대하다. 여러 노드 서버가있는 경우, 하나는 다른 사람에게 메시지를 푸시 할 수 있습니다.
레디 스 펍 / 서브 경우 모든 클라이언트가 레디 스에 직접 액세스 할 중대하다. 여러 노드 서버가있는 경우, 하나는 다른 사람에게 메시지를 푸시 할 수 있습니다.
당신은 또한 브라우저에서 클라이언트가있는 경우에, 당신은 클라이언트에 서버에서 푸시 데이터에 다른 뭔가를해야하고,이 경우, socket.io는 중대하다.
당신은 레디 스 저장소와 socket.io를 사용하는 경우 이제, socket.io는 서버간에 메시지를 전달하기 위해 후드 레디 스 펍 / 서브를 사용하고, 서버는 클라이언트에 메시지를 전달합니다.
레디 스 저장소로 구성 socket.io와 socket.io 객실을 사용 그래서 아마 당신을위한 간단합니다.
-
==============================
2.나는 그것을 위해 사용을 찾을 수 밖에 일반적으로 생각 된 사람에서 작동합니다 많은 술집 서브 클라이언트를 허용하지만 대신 모든 단일 socketio 연결에 새로운 2 개 레디 스 연결을 요구하는 플러그인 노드를 작성 끝났다.
나는 그것을 위해 사용을 찾을 수 밖에 일반적으로 생각 된 사람에서 작동합니다 많은 술집 서브 클라이언트를 허용하지만 대신 모든 단일 socketio 연결에 새로운 2 개 레디 스 연결을 요구하는 플러그인 노드를 작성 끝났다.
이 코드는 기본적으로이 예에서 socket.io 클라이언트의 수를 연결하여 항상 여전히 2 개 레디 스 연결을 사용하지만, 모든 클라이언트가 자신의 채널에 가입 할 수 있습니다, socket.io 실행 및 설정을 가정한다. 이 예에서 모든 클라이언트는 메시지 '달콤한 메시지를!'가져 10 초 후에.
socket.io 예는 (레디 스 이용하는 바-SUB)
var RPubSubFactory = require('rpss.js'); var redOne = redis.createClient(port, host), redTwo = redis.createClient(port, host); var pSCFactory = new RPubSubFactory(redOne); io.sockets.on('connection', function(socket){ var cps = pSCFactory.createClient(); cps.onMessage(function(channel, message){ socket.emit('message', message); }); io.sockets.on('disconnect', function(socket){ // Dont actually need to unsub, because end() will cleanup all subs, // but if you need to sometime during the connection lifetime, you can. cps.unsubscribe('cool_channel'); cps.end(); }); cps.subscribe('cool_channel') }); setTimeout(function(){ redTwo.publish('cool_channel', 'sweet message!'); },10000);
실제 플러그인 코드 :
var RPubSubFactory = function(){ var len,indx,tarr; var dbcom = false, rPubSubIdCounter = 1, clientLookup = {}, globalSubscriptions = {}; // public this.createClient = function() { return new RPubSupClient(); } // private var constructor = function(tdbcom) { dbcom = tdbcom; dbcom.on("message", incommingMessage); } var incommingMessage = function(rawchannel, strMessage) { len = globalSubscriptions[rawchannel].length; for(var i=0;i<len;i++){ //console.log(globalSubscriptions[rawchannel][i]+' incomming on channel '+rawchannel); clientLookup[globalSubscriptions[rawchannel][i]]._incommingMessage(rawchannel, strMessage); } } // class var RPubSupClient = function() { var id = -1, localSubscriptions = []; this.id = -1; this._incommingMessage = function(){}; this.subscribe = function(channel) { //console.log('client '+id+' subscribing to '+channel); if(!(channel in globalSubscriptions)){ globalSubscriptions[channel] = [id]; dbcom.subscribe(channel); } else if(globalSubscriptions[channel].indexOf(id) == -1){ globalSubscriptions[channel].push(id); } if(localSubscriptions.indexOf(channel) == -1){ localSubscriptions.push(channel); } } this.unsubscribe = function(channel) { //console.log('client '+id+' unsubscribing to '+channel); if(channel in globalSubscriptions) { indx = globalSubscriptions[channel].indexOf(id); if(indx != -1){ globalSubscriptions[channel].splice(indx, 1); if(globalSubscriptions[channel].length == 0){ delete globalSubscriptions[channel]; dbcom.unsubscribe(channel); } } } indx = localSubscriptions.indexOf(channel); if(indx != -1){ localSubscriptions.splice(indx, 1); } } this.onMessage = function(msgFn) { this._incommingMessage = msgFn; } this.end = function() { //console.log('end client id = '+id+' closing subscriptions='+localSubscriptions.join(',')); tarr = localSubscriptions.slice(0); len = tarr.length; for(var i=0;i<len;i++){ this.unsubscribe(tarr[i]); } localSubscriptions = []; delete clientLookup[id]; } var constructor = function(){ this.id = id = rPubSubIdCounter++; clientLookup[id] = this; //console.log('new client id = '+id); } constructor.apply(this, arguments); } constructor.apply(this, arguments); }; module.exports = RPubSubFactory;
나는 주변 청소 만하고 있지만, 일부 다른 속도 테스트를 수행 한 후, 나는 이것이 가장 빠른 내가 그것을 얻을 수이었다 결론을 내렸다 내가 할 수있는만큼 효율성을 개선하기 위해 노력했다.
최신 버전의 경우 : https://github.com/Jezternz/node-redis-pubsub
from https://stackoverflow.com/questions/14929700/what-should-i-be-using-socket-io-rooms-or-redis-pub-sub by cc-by-sa and MIT license
'REDIS' 카테고리의 다른 글
[REDIS] 레디 스 : 키의 표시는 데이터베이스 크기 / 크기 (0) | 2020.01.01 |
---|---|
[REDIS] 레디 스 관리 패널 [폐쇄] (0) | 2020.01.01 |
[REDIS] 레디 스 및 Memcache를하거나 레디 스? (0) | 2020.01.01 |
[REDIS] Node.js를 데이터베이스 [폐쇄] (0) | 2020.01.01 |
[REDIS] beanstalkd 대 resque 대 delayed_jobs? (0) | 2020.01.01 |