
当使用多个 Discord.js 客户端(如 client 和 clientHook)时,若在事件监听中误用非目标客户端的缓存或方法,会导致本应由 clientHook 执行的操作(如加入语音频道)被 client 错误触发——根本原因在于混用了客户端实例。
当使用多个 discord.js 客户端(如 `client` 和 `clienthook`)时,若在事件监听中误用非目标客户端的缓存或方法,会导致本应由 `clienthook` 执行的操作(如加入语音频道)被 `client` 错误触发——根本原因在于混用了客户端实例。
在你的代码中,问题出在这一行:
adapterCreator: client.guilds.cache.get("1148582522633072741").voiceAdapterCreator,
虽然事件监听器绑定在 clientHook 上(clientHook.on("messageCreate", ...)),但你却调用了 client.guilds.cache.get(...) —— 这意味着你正在从另一个机器人实例(client)中获取语音适配器。Discord.js 的 joinVoiceChannel() 本身不持有客户端上下文,它依赖传入的 adapterCreator 所属的客户端来建立连接。一旦 adapterCreator 来自 client,底层音频连接就会关联到 client,导致 client 实际加入语音频道,而非 clientHook。
✅ 正确做法是:确保所有与客户端相关的资源(如 guild 缓存、adapterCreator、user ID 检查等)均来自当前处理事件的客户端实例。因此,应将 client 替换为 clientHook:
clientHook.on("messageCreate", async (message) => {
if (message.author.bot && message.content.startsWith("You casted")) {
joinVoiceChannel({
channelId: Fishgame[castStrength],
guildId: "1148582522633072741",
adapterCreator: clientHook.guilds.cache.get("1148582522633072741")?.voiceAdapterCreator,
});
}
});
⚠️ 注意事项:
将一个或多个视频上传至YouTube。当用户想“上传到YouTube”“发YouTube”“批量上传”“upload to YouTube”“post videos to YouTube”或发布到YouTube时使用此技能。
- 使用可选链操作符
?.防止因 guild 未缓存或未就绪导致voiceAdapterCreator为undefined; - 确保
clientHook已登录且已加载目标服务器(可通过clientHook.guilds.cache.has("1148582522633072741")校验); - 若
joinVoiceChannel是自定义封装函数(例如来自@discordjs/voice),强烈建议重构其签名,显式接收客户端实例,提升可维护性与安全性:
// 推荐:增强可扩展性与明确性
function joinVoiceChannel(
options: { channelId: string; guildId: string; },
client: Client // ← 显式传入所属 client
) {
const guild = client.guilds.cache.get(options.guildId);
if (!guild) throw new Error(`Guild ${options.guildId} not found on provided client`);
return entersVoiceChannel({
channelId: options.channelId,
guildId: options.guildId,
adapterCreator: guild.voiceAdapterCreator,
});
}
然后调用:
joinVoiceChannel({ channelId: Fishgame[castStrength], guildId: "1148582522633072741" }, clientHook);
这样不仅彻底规避跨客户端误用风险,还使逻辑职责清晰、便于单元测试与多实例管理。多机器人架构下,“谁触发、谁负责”是避免干扰的核心原则。










