Discord.js v14分页交互异常:deferReply失效及优化方案求助
Discord.js v14 嵌入分页按钮交互异常解决办法
在Discord.js v14中,组件交互(如按钮点击)必须在3秒内得到响应,否则会触发交互失败提示。你遇到的核心问题是没有用正确的方式响应按钮交互:
- 使用
i.deferReply()会创建新的独立回复,导致原消息的按钮失去关联,持续显示“Bot is thinking...” - 不响应则会触发“This interaction failed”提示
正确解决方案
使用i.deferUpdate()方法,它专门用于告知Discord:你将更新原交互消息,不会生成新回复,也不会保留“思考”状态,完美适配分页场景。
修改后的完整代码
const { ActionRowBuilder, ButtonBuilder, ButtonStyle, ComponentType, EmbedBuilder } = require('discord.js'); module.exports = { async execute(interaction, pages, time = 60000) { await interaction.deferReply(); if (pages.length === 1) { const page = await interaction.editReply({ embeds: [pages[0]], components: [], fetchReply: true }); return page; } const prev = new ButtonBuilder() .setCustomId('prev') .setEmoji('◀️') .setStyle(ButtonStyle.Primary) .setDisabled(true); const home = new ButtonBuilder() .setCustomId('home') .setEmoji('🏠') .setStyle(ButtonStyle.Secondary) .setDisabled(true); const next = new ButtonBuilder() .setCustomId('next') .setEmoji('▶️') .setStyle(ButtonStyle.Primary); const buttonRow = new ActionRowBuilder() .addComponents(prev, home, next); let index = 0; let currentPage = await interaction.editReply({ embeds: [pages[index]], components: [buttonRow], fetchReply: true }); const collector = currentPage.createMessageComponentCollector({ componentType: ComponentType.Button, time }); collector.on('collect', async (i) => { if (i.user.id !== interaction.user.id) { const embed = new EmbedBuilder() .setDescription('You can\'t use these buttons!'); return i.reply({ embeds: [embed], ephemeral: true }); } // 关键修改:用deferUpdate响应交互,告知Discord将更新原消息 await i.deferUpdate(); if (i.customId === 'prev') { if (index > 0) index--; } else if (i.customId === 'home') { index = 0; } else if (i.customId === 'next') { if (index < pages.length - 1) index++; } // 更新按钮状态 prev.setDisabled(index === 0); home.setDisabled(index === 0); next.setDisabled(index === pages.length - 1); // 更新原消息内容 await currentPage.edit({ embeds: [pages[index]], components: [buttonRow] }); collector.resetTimer(); }); collector.on('end', async () => { await currentPage.edit({ embeds: [pages[index]], components: [] }); }); return currentPage; } };
额外细节修正
- 修复了单页面场景的数组引用错误:原代码
embeds: [pages]改为embeds: [pages[0]],确保正确取到单页内容 - 简化按钮状态判断逻辑,用
prev.setDisabled(index === 0)这种更简洁的写法替代分支判断 - 为所有异步操作添加
await,避免Promise未处理导致的潜在问题
内容的提问来源于stack exchange,提问作者Binary Bytes
相关产品推荐
相关产品推荐

