
discord.py 的交互式按钮默认 3 分钟后自动失效,导致用户点击时提示 “interaction failed”;只需为 view 设置 timeout=none 即可永久启用,若需重启后仍有效,还需启用持久化视图(persistent views)。
discord.py 的交互式按钮默认 3 分钟后自动失效,导致用户点击时提示 “interaction failed”;只需为 view 设置 timeout=none 即可永久启用,若需重启后仍有效,还需启用持久化视图(persistent views)。
在你的代码中,SuggestionButtonView 继承自 discord.ui.View,但未显式指定 timeout 参数。根据 discord.py 文档,默认超时时间为 180 秒(3 分钟) —— 这正是你观察到“前 5 分钟可用,之后点击报错 Interaction failed”的根本原因。Discord 会在超时后自动禁用该 View 中所有组件(包括按钮),后续交互将被拒绝。
✅ 正确修复:禁用超时(适用于短期运行场景)
修改 SuggestionButtonView 类定义,显式传入 timeout=None:
class SuggestionButtonView(discord.ui.View):
def __init__(self):
super().__init__(timeout=None) # 关键:禁用自动超时
@discord.ui.button(label="Enviar Sugestão", style=discord.ButtonStyle.primary, custom_id="send_suggestion")
async def button_click(self, interaction: discord.Interaction, button: discord.ui.Button):
modal = SuggestionModal()
await interaction.response.send_modal(modal)
⚠️ 注意:timeout=None 表示「永不过期」,但仅限当前 bot 实例生命周期内有效。一旦 bot 重启,所有未持久化的 View 将丢失状态,按钮点击会返回 404 Not Found 或 Interaction failed。
? 进阶方案:启用持久化视图(推荐生产环境使用)
若需 bot 重启后按钮仍可响应,必须启用 Persistent View —— 要求:
- 所有 View 实例必须在 bot 启动时通过 bot.add_view() 注册;
- 每个 Button 必须设置唯一且固定不变的 custom_id(你已正确设置了 "send_suggestion");
- View 初始化时传入 timeout=None 并确保不依赖运行时动态状态(如闭包变量、未序列化对象)。
✅ 修改启动逻辑(例如在 on_ready 中注册):
@bot.event
async def on_ready():
print(f'Bot {bot.user} está online.')
# 注册持久化 View —— 必须在 bot 启动后立即执行一次
bot.add_view(SuggestionButtonView())
同时,更新 View 类以支持持久化(保持 custom_id 稳定 + 显式 timeout):
class SuggestionButtonView(discord.ui.View):
def __init__(self):
super().__init__(timeout=None) # 必须设为 None 或足够长的值
@discord.ui.button(label="Enviar Sugestão", style=discord.ButtonStyle.primary, custom_id="send_suggestion")
async def button_click(self, interaction: discord.Interaction, button: discord.ui.Button):
modal = SuggestionModal()
await interaction.response.send_modal(modal)
并在 /add_button 命令中直接复用该 View(无需每次新建):
@bot.tree.command(name='add_button', description='Adicione um botão para enviar sugestões.')
@app_commands.checks.check(check_roles)
async def add_button(interaction: discord.Interaction):
try:
embed = discord.Embed(
title="Envie sua Sugestão",
description="Clique no botão abaixo para enviar sua sugestão!\n\n Com seu feedback conseguimos melhorar em vários aspectos!",
color=discord.Color.gold()
)
embed.set_author(name="Sistema de Sugestões")
embed.set_image(url="https://cdn.discordapp.com/attachments/...") # 保持原 URL
embed.set_footer(text="BOT Powered by Rodopoulos")
view = SuggestionButtonView() # 复用已注册的持久化 View
await interaction.response.send_message(embed=embed, view=view)
except Exception as e:
print(f"Erro ao adicionar botão de sugestões: {e}")
await interaction.response.send_message("Erro ao adicionar botão de sugestões。Por favor, tente novamente mais tarde。", ephemeral=True)
? 关键总结
- ❌ 错误认知:“按钮失效是权限或网络问题” → 实际是 View 超时机制触发;
- ✅ 快速修复:View(timeout=None) 解决短期失效;
- ✅ 生产必备:bot.add_view() + 固定 custom_id + timeout=None 实现重启不中断;
- ? 避免陷阱:不要在 View 中存储不可序列化对象(如 interaction.guild 引用),否则持久化会失败。
遵循以上配置,你的 /add_button 发送的按钮将长期稳定响应,彻底告别 “Interaction failed”。











