我正在使用node.js和socket.io创建一个包含多个游戏室的游戏大厅。我想要做的是阻止用户在多个选项卡中打开大厅。我的想法是,当打开一个新标签时,断开前一个标签。我想我可以通过跟踪已经打开的标签的socket.id来实现这一点。
//Keep track of the online users
var onlineUsers = new Array();
sessionSockets.on('connection', function(err, socket, session){
socket.on('joinlobby', function(){
//Disconnect the users previous socket if their username is already in the onlineUser array
console.log("DISCONNECTED: " + onlineUsers[session.username]);
socket.disconnect(onlineUsers[session.username]);
onlineUsers[session.username] = socket.id;
console.log("CONNECTED: " + onlineUsers[session.username]);
});
});
首次加载页面时会触发Joinlobby。我正在使用session.socket.io,因此我可以访问套接字中的会话数据。我使用用户名作为数组键,并存储当前的socket.id。现在我遇到的问题似乎是行为有点不一致。有时它什么都不做,两个标签都没有断开连接,而有时候两个标签都断开连接。控制台中没有错误,所以任何人都可以看到我的方法有问题吗?控制台输出的一个示例是:
DISCONNECTED: dOW2y-fq-aDW7t0sRUKn
info - booting client
info - transport end by forced client disconnection
info - transport end (booted)
CONNECTED: 9vZbMC85x9OQsFo9RUKo
即使它说连接,它也不会让我发送或接收任何消息。任何帮助将不胜感激,谢谢。
答案 0 :(得分:1)
socket.disconnect(onlineUsers[session.username]);
你实际上是在断开新套接字而不是旧套接字。
如果你有一个指向旧套接字的指针,请调用.disconnect()
。
类似的东西:
var sockets = { };
sessionSockets.on('connection', function(err, socket, session){
sockets[socket.id] = socket;
socket.on('joinlobby', function(){
//Disconnect the users previous socket if their username is already in the onlineUser array
var onlineSocketID = onlineUsers[session.username];
if (onlineSocketID && onlineSocketID !== socket.id) {
console.log("DISCONNECTED: " + onlineUsers[session.username]);
sockets[onlineSocketID].disconnect();
delete sockets[onlineSocketID];
}
if (onlineSocketID !== socket.id) {
onlineUsers[session.username] = socket.id;
console.log("CONNECTED: " + onlineUsers[session.username]);
}
});
});
此处作为额外评论 - 我个人不会根据用户名识别用户,但会使用内部用户ID,但这取决于您的应用程序逻辑。
同样使用该逻辑,如果你从客户端发送两次“joinlobby”消息,它将导致自我断开,所以我也添加了检查。