From f309641bb7aa998f222b73f4d0d2d2a38f209871 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marek=20Farka=C5=A1?= Date: Sun, 16 Feb 2025 13:41:06 +0100 Subject: [PATCH] bugfix for anti spam --- server/index.js | 53 +++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 53 insertions(+) diff --git a/server/index.js b/server/index.js index 501c2b3..88e28a4 100644 --- a/server/index.js +++ b/server/index.js @@ -326,6 +326,59 @@ app.set('view engine', 'ejs'); app.set('views', path.join(__dirname, '../web')); app.use('/', endpoints); +function antispamProtection(message, clientIp, ws, userCommands, lastWarn, userCommandHistory, lengthCommands, endpointName) { + const command = message.toString(); + const now = Date.now(); + if (endpointName === 'text') logDebug(`Command received from \x1b[90m${clientIp}\x1b[0m: ${command}`); + // Initialize user command history if not present + if (!userCommandHistory[clientIp]) { + userCommandHistory[clientIp] = []; + } + + // Record the current timestamp for the user + userCommandHistory[clientIp].push(now); + + // Remove timestamps older than 20 ms from the history + userCommandHistory[clientIp] = userCommandHistory[clientIp].filter(timestamp => now - timestamp <= 20); + + // Check if there are 8 or more commands in the last 20 ms + if (userCommandHistory[clientIp].length >= 8) { + logWarn(`User \x1b[90m${clientIp}\x1b[0m is spamming with rapid commands. Connection will be terminated and user will be banned.`); + + // Add to banlist if not already banned + if (!serverConfig.webserver.banlist.includes(clientIp)) { + serverConfig.webserver.banlist.push(clientIp); + logInfo(`User \x1b[90m${clientIp}\x1b[0m has been added to the banlist due to extreme spam.`); + console.log(serverConfig.webserver.banlist); + configSave(); + } + + ws.close(1008, 'Bot-like behavior detected'); + return command; // Return command value before closing connection + } + // Update the last message time for general spam detection + lastMessageTime = now; + // Initialize command history for rate-limiting checks + if (!userCommands[command]) { + userCommands[command] = []; + } + // Record the current timestamp for this command + userCommands[command].push(now); + // Remove timestamps older than 1 second + userCommands[command] = userCommands[command].filter(timestamp => now - timestamp <= 1000); + // If command count exceeds limit, close connection + if (userCommands[command].length > lengthCommands) { + if (now - lastWarn.time > 1000) { // Check if 1 second has passed + logWarn(`User \x1b[90m${clientIp}\x1b[0m is spamming command "${command}" in /${endpointName}. Connection will be terminated.`); + lastWarn.time = now; // Update the last warning time + } + ws.close(1008, 'Spamming detected'); + return command; // Return command value before closing connection + } + return command; // Return command value for normal execution +} + + /** * WEBSOCKET BLOCK */