Node.js中Kahoot Bot同名重复报错:Socket清理后仍无效求助
解决Kahoot机器人「Duplicate name」重复名称错误
问题根源分析
- 服务器端缓存机制:Kahoot服务器会对已登录的玩家名称做短期会话缓存,即便客户端主动断开连接,服务器不会立刻释放该名称,需要等待会话超时(通常几秒到十几秒)。
- 现有清理逻辑的缺陷:
- 代码中定义的是单个
bot变量,但进程退出监听里循环的是未定义的bots,导致清理逻辑根本没执行。 bot.leave()是异步操作,你直接同步执行后续的socket关闭、监听器移除,可能leave()还没完成就切断了连接,服务器没收到注销请求,自然不会释放名称。
- 代码中定义的是单个
修正后的代码
const Kahoot = require("kahoot.js-latest"); const colors = require('colors'); const bot = new Kahoot(); async function cleanup() { try { // 先等待leave执行完成,确保服务器收到注销请求 await bot.leave(); } catch (err) { console.log("Leave failed:".red, err); } // 移除所有监听器 bot.removeAllListeners(); // 安全关闭socket连接 if (bot.socket) { bot.socket.close(); bot.socket.terminate(); } } // 替换为异步登录逻辑,配合错误处理 async function initBot() { try { await bot.join(process.argv[2], "a"); console.log("Joining...".cyan); } catch (err) { console.log(err); await cleanup(); process.exit(1); } } initBot(); // 处理进程退出事件 ["exit", "SIGINT", "SIGUSR1", "SIGUSR2", "SIGTERM"].forEach((eventType) => { process.on(eventType, async (code) => { await cleanup(); console.log("Exiting Process with code: ".yellow + code); process.exit(code); }); });
额外优化建议
如果修正后仍出现重复名称错误,说明服务器缓存还未释放,可以添加重试逻辑:
async function tryJoin(gameId, name) { let attempts = 3; while (attempts > 0) { try { await bot.join(gameId, name); console.log("Joined successfully!".cyan); return; } catch (err) { if (err.description === 'Duplicate name' && attempts > 1) { console.log("Name still in use, retrying in 3 seconds...".yellow); await new Promise(resolve => setTimeout(resolve, 3000)); attempts--; } else { throw err; } } } throw new Error("Failed to join after multiple attempts"); } // 使用重试逻辑替代直接登录 async function initBot() { try { await tryJoin(process.argv[2], "a"); } catch (err) { console.log(err); await cleanup(); process.exit(1); } } initBot();
另外可以检查kahoot.js-latest库的leave()方法源码,确认它是否正确向服务器发送了注销消息,如果库本身存在实现缺陷,可能需要手动构造socket消息发送注销请求。
内容的提问来源于stack exchange,提问作者Coll y
相关产品推荐
相关产品推荐

