105 lines
3.6 KiB
JavaScript
105 lines
3.6 KiB
JavaScript
const path = require("path");
|
|
require("dotenv").config({
|
|
path: path.resolve(process.cwd(), `.env.${process.env.NODE_ENV || "development"}`)
|
|
});
|
|
const logger = require("../utils/logger");
|
|
const { admin } = require("../firebase/firebase-handler");
|
|
|
|
// Logging helper functions
|
|
function createLogEvent(socket, level, message) {
|
|
console.log(`[IOREDIS LOG EVENT] - ${socket.user.email} - ${socket.id} - ${message}`);
|
|
logger.log("ioredis-log-event", level, socket.user.email, null, { wsmessage: message });
|
|
}
|
|
|
|
const redisSocketEvents = (io, { addUserToRoom, getUsersInRoom, removeUserFromRoom }) => {
|
|
// Room management and broadcasting events
|
|
function registerRoomAndBroadcastEvents(socket) {
|
|
socket.on("join-bodyshop-room", async (bodyshopUUID) => {
|
|
socket.join(bodyshopUUID);
|
|
await addUserToRoom(bodyshopUUID, { uid: socket.user.uid, email: socket.user.email });
|
|
createLogEvent(socket, "DEBUG", `Client joined bodyshop room: ${bodyshopUUID}`);
|
|
|
|
// Notify all users in the room about the updated user list
|
|
const usersInRoom = await getUsersInRoom(bodyshopUUID);
|
|
io.to(bodyshopUUID).emit("room-users-updated", usersInRoom);
|
|
});
|
|
|
|
socket.on("leave-bodyshop-room", async (bodyshopUUID) => {
|
|
socket.leave(bodyshopUUID);
|
|
createLogEvent(socket, "DEBUG", `Client left bodyshop room: ${bodyshopUUID}`);
|
|
});
|
|
|
|
socket.on("get-room-users", async (bodyshopUUID, callback) => {
|
|
const usersInRoom = await getUsersInRoom(bodyshopUUID);
|
|
callback(usersInRoom);
|
|
});
|
|
|
|
socket.on("broadcast-to-bodyshop", async (bodyshopUUID, message) => {
|
|
io.to(bodyshopUUID).emit("bodyshop-message", message);
|
|
createLogEvent(socket, "INFO", `Broadcast message to bodyshop ${bodyshopUUID}`);
|
|
});
|
|
|
|
socket.on("disconnect", async () => {
|
|
createLogEvent(socket, "DEBUG", `User disconnected.`);
|
|
|
|
// Get all rooms the socket is part of
|
|
const rooms = Array.from(socket.rooms).filter((room) => room !== socket.id);
|
|
|
|
for (const bodyshopUUID of rooms) {
|
|
await removeUserFromRoom(bodyshopUUID, { uid: socket.user.uid, email: socket.user.email });
|
|
|
|
// Notify all users in the room about the updated user list
|
|
const usersInRoom = await getUsersInRoom(bodyshopUUID);
|
|
io.to(bodyshopUUID).emit("room-users-updated", usersInRoom);
|
|
}
|
|
});
|
|
}
|
|
|
|
// Register all socket events for a given socket connection
|
|
function registerSocketEvents(socket) {
|
|
createLogEvent(socket, "DEBUG", `Connected and Authenticated.`);
|
|
|
|
// Register room and broadcasting events
|
|
registerRoomAndBroadcastEvents(socket);
|
|
|
|
// Handle socket disconnection
|
|
socket.on("disconnect", async () => {
|
|
createLogEvent(socket, "DEBUG", `User disconnected.`);
|
|
});
|
|
}
|
|
|
|
const authMiddleware = (socket, next) => {
|
|
try {
|
|
if (socket.handshake.auth.token) {
|
|
admin
|
|
.auth()
|
|
.verifyIdToken(socket.handshake.auth.token)
|
|
.then((user) => {
|
|
socket.user = user;
|
|
next();
|
|
})
|
|
.catch((error) => {
|
|
next(new Error("Authentication error", JSON.stringify(error)));
|
|
});
|
|
} else {
|
|
next(new Error("Authentication error - no authorization token."));
|
|
}
|
|
} catch (error) {
|
|
console.log("Uncaught connection error:::", error);
|
|
logger.log("websocket-connection-error", "error", null, null, {
|
|
token: socket.handshake.auth.token,
|
|
...error
|
|
});
|
|
next(new Error(`Authentication error ${error}`));
|
|
}
|
|
};
|
|
|
|
// Socket.IO Middleware and Connection
|
|
io.use(authMiddleware);
|
|
io.on("connection", registerSocketEvents);
|
|
};
|
|
|
|
module.exports = {
|
|
redisSocketEvents
|
|
};
|