Discord Bot执行ban命令后无论是否成功都报错退出如何解决
问题根因
- ban逻辑位置错误:你把用户提取、ban操作的代码放在了前缀判断、命令识别之前,所有收到的消息(不管是不是+ban命令,甚至不带前缀的普通消息)都会触发ban调用,当消息没有@用户时,你给ban方法传入了undefined参数,直接触发
Error [BAN_RESOLVE_ID]错误。
- ban逻辑位置错误:你把用户提取、ban操作的代码放在了前缀判断、命令识别之前,所有收到的消息(不管是不是+ban命令,甚至不带前缀的普通消息)都会触发ban调用,当消息没有@用户时,你给ban方法传入了undefined参数,直接触发
- 异步操作未捕获异常:
guild.members.ban()是异步Promise方法,你没有添加错误捕获逻辑,一旦API返回错误(比如目标用户角色权限高于Bot、网络波动等),未处理的Promise rejection会直接导致进程退出。
- 异步操作未捕获异常:
- 重复执行ban操作:你预先执行了
banMember = msg.guild.members.ban(user),之后在ban命令分支又写了banMember;相当于又触发一次ban调用,重复请求Discord API也会触发限流或权限错误。
- 重复执行ban操作:你预先执行了
修复方案
替换你的message事件逻辑即可,修复后的完整代码如下:
const Discord = require('discord.js'); const client = new Discord.Client(); const prefix = "+"; // 全局兜底捕获未处理异步错误,避免进程意外退出 process.on('unhandledRejection', error => { console.error('未处理的异步错误:', error); }); client.on('ready', () => { console.log(`Logged in as ${client.user.tag}!`); }); client.on('message', async msg => { // 先过滤非命令消息 if (!msg.content.startsWith(prefix)) return; const { content } = msg; let latency = Date.now() - msg.createdTimestamp; let latencyOfAPI = Math.round(client.ws.ping); const args = content.slice(prefix.length).trim().split(/ +/g); const command = args.shift().toLowerCase(); switch(command) { case "ping" : { msg.reply("This is the latency between the message and the response: " + latency + "." + "\nThis is the API latency: " + latencyOfAPI + "."); break; } case "pong" : { msg.reply("ping"); break } case "ban" : { // 仅触发ban命令时才提取用户、执行封禁操作 const user = msg.mentions.users.first(); if (user) { try { // 等待异步封禁结果,捕获所有可能的异常 await msg.guild.members.ban(user); msg.reply("The user " + user + " has been banned.") } catch (err) { console.error("封禁失败:", err); msg.reply("封禁操作失败,请检查Bot权限和目标用户身份。") } } else { return msg.reply("There is no one to ban.") } break } } }); client.login('你的Bot Token')
额外优化建议
- 可以添加调用者权限判断,只有拥有服务器封禁权限的用户才能调用ban命令,避免普通用户滥用
- 可以扩展封禁理由参数,封禁时同时记录原因方便服务器管理
内容的提问来源于stack exchange,提问作者Arian
相关产品推荐
相关产品推荐

