'socket.io the room in the rooms dictionary is 'undefined'?
so I'm emitting an event from my client that sends a string containing the socket/roomID I'm trying to connect to in it. When the data is received, it's handled by this code on the server side:
const express = require('express');
const app = express();
const http = require('http').Server(app);
const io = require('socket.io')(http);
const port = process.env.PORT || 3000;
app.use(express.static(__dirname + '/public'));
//runs when the user connects to the server
function onConnection(socket){
console.log('a user connected');
// socket.join('some room');
console.log('Created Room: ' + socket.id);
socket.emit("RoomID", socket.id);
socket.on("location", (receivedString) => {
// socket.emit("RoomID", socket.id);
socket.to(socket.id).emit("redirectLocation", receivedString);
console.log('\nReceived the following data from socket "' + socket.id + '": ' + receivedString);
console.log('The amount of people in this room is ' + io.sockets.adapter.rooms.get(socket.id).size + '.');
});
//runs when the user is trying to join a specific room
socket.on("joinRoom", (roomIdentifier) => {
console.log('The room identifier is: ' + roomIdentifier);
console.log('The room is already in the rooms array: ' + io.sockets.adapter.rooms[String(roomIdentifier)]);
if (io.sockets.adapter.rooms[roomIdentifier]) {
socket.join(roomIdentifier);
} else {
console.log(socket.id + 'tried to join ' + roomIdentifier + 'but the room does not exist.');
};
});
socket.on('disconnect', onDisconnection);
}
//runs when the user disconnects from the server
function onDisconnection(socket){
console.log('a user disconnected');
}
//runs when the socket manager registers a connection
io.on('connection', onConnection);
//Runs when a new room was created
io.of("/").adapter.on("create-room", (room) => {
console.log(`room ${room} was created`);
});
io.of("/").adapter.on("join-room", (room, id) => {
console.log(`socket ${id} has joined room ${room}`);
});
http.listen(port, () => console.log('listening on port ' + port));
I don't know why it's coming out as undefined--I thought maybe it was because the rooms dictionary wasn't supposed to have a string or something as a key but I'm really not sure.
Solution 1:[1]
There are two problems in the code shared:
Check whether a room already exists
The following command shows that io.sockets.adapter.rooms
is a JavaScript Map
object.
console.log(io.sockets.adapter.rooms)
// returns [object Map]
To check whether the Map contains the room name, the Map.has(key)
should then be used, instead of Map[key]
:
io.sockets.adapter.rooms.has(roomIdentifier)
Once the room existence checks are adapted as above, the code still fails to let users join a room, as explained below.
Joining a room
The if
statement lets the user join a room only if the room already exists, and does nothing otherwise. As a consequence, rooms are never created, and hence no user can ever join any of them.
if (io.sockets.adapter.rooms.has(roomIdentifier)) {
socket.join(roomIdentifier);
} else {
console.log(socket.id + 'tried to join ' + roomIdentifier + 'but the room does not exist.');
// Socket.join is not executed, hence the room not created.
};
socket.join
should be executed outside of the if
statement. The if
statement can probably be removed from the code, unless some specific action needs to be taken depending on it.
if (io.sockets.adapter.rooms.has(roomIdentifier)) {
// action when room already exists
} else {
console.log(socket.id + 'tried to join ' + roomIdentifier + 'but the room does not exist.');
// action when room is new
};
// join the room in any case
socket.join(roomIdentifier);
Solution 2:[2]
Try using io.sockets.adapter.rooms.get(roomId)
io.sockets.adapter.rooms returns a Map Object so using io.sockets.adapter.rooms[roomId]
returns undefined.
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
Solution | Source |
---|---|
Solution 1 | Arnav Thorat |
Solution 2 | M2K Developments |