2016-05-10 12 views
2

Expressアプリケーションで特定のルートにアクセスするときにsocket.IOルームに参加する際に問題が発生しました。Expressルートにアクセスしたときにsocket.IOルームに参加する

だから私は現在、以下を設定している:

app.js

var express = require('express'); 
var app = express(); 
var http = require('http').Server(app); 
var socketio = require('socket.io').listen(http); 
var socketjs = require(libs + 'sockets/socket.js'); 

... 

var server = http.listen(app.get('port'), function() { 
    debug('Taskful server listening on port ' + app.get('port')); 
    log.info('Taskful server listening on port ' + app.get('port')); 
}); 

global.socketIO = socketio; 
socketjs.connect(server); 

ソケット/ socket.js

var libs = process.cwd() + '/libs/'; 
var log = require(libs + 'log')(module); 

module.exports.connect = function(server) { 
    var io = global.socketIO; 

    io.on('connection', function (socket) { 
    //This comes through 
     log.info('Connection to socket.io'); 
    }); 
} 

ルート - projects.js

var io = global.socketIO; 

... 

router.get('/:id', function(req, res) { 
    projectController.findByIdExtended(req, res, function(err, ret) { 
     if (err) { 
      res.redirect('/projects'); 
     } 
     req.session.viewingProject = req.params.id; 

     //I would like to be able to join the room here 
     io.room = 'project_' + req.session.viewingProject; 
     io.join(io.room); 

     var db_project = ret[0]; 
     var db_tasks = ret[1]; 

     res.render('project', { user : req.user, project : db_project, tasks: db_tasks }); 
    }); 
}); 

コメントと同じように、ルートにアクセスするとソケットIOルームに参加したいと思います。

私はio.sockets.joinを試しましたが、それらはすべて機能していないものです。私はそれをコンソールログに見ることができるので、グローバルIOスコープは間違いなくあります。

EventEmittersでこれを行うのは簡単ですが、socket.jsファイル内のイベントに参加するだけですか?もしそうなら、どのようにすればよいのでしょうか?

何か助けていただければ幸いです。

答えて

0

socket.join()は、特定のsocket.ioソケットに接続してください。 io.join()またはio.sockets.join()には電話をしないでください。その上

socket.join('project_' + req.session.viewingProject); 

を:だから、あなたが部屋に入れて、あなたが呼び出したい特定のsocketオブジェクトを取得する必要があります。

現在のルート要求を行ったユーザに関連付けられた特定のsocketを取得しようとする場合は、ソケットとルートの間の関連付けを設定する必要があります(通常、既知のCookie識別子を使用します)。ルートからそのクッキー値を検索し、それを使用して現在のユーザーに対して正しいsocketオブジェクトを見つけることができます。

すでにセッションを使用しているように見えるので、ルートを特定のsocket.io接続に関連付けるために使用できるCookie識別子がすでに存在するはずです。これらの2つをio.on('connection')socket.on('disconnect')に関連付けるマップオブジェクトを作成する必要があるかもしれません。そのため、セッションIDをフェッチして、そのマップ内の正しいソケットオブジェクトをルックアップできます。


注:あなたの使用:モジュール変数としてprojects.jsの開始時

var io = global.socketIO; 

抗パターンのビットです。これにより、projects.jsモジュールがロードされる前にglobal.socketIOへの代入を行う必要があるか、コードが機能しなくなるモジュールロードタイミングの依存関係が作成されます。特に、循環依存性を持つモジュールタイミングは複雑な問題になる可能性があるため、これは作成または持たせるのが望ましい状況ではありません。

コードをわずかに変更して、グローバルをまったく使用しないようにします(socketIOの値をプロジェクトに明示的に渡すことによって)。jsコンストラクタ)、ローカル変数として必要な各ルートにvar io = global.socketIO;を移動するだけで、このロードタイミングの依存関係が完全に削除されます。

関連する問題