Discord.py开发snipe命令出现跨频道捕获已删消息问题如何解决
问题根因
你当前的bot.sniped_messages字典仅使用服务器ID作为唯一键,每个服务器只会存储全局最新的1条已删除消息,没有按频道做隔离,因此执行snipe命令时只会返回整服最近被删的消息,和你当前执行命令的频道无关。
修复方案
调整存储结构,使用(服务器ID, 频道ID)的元组作为存储键,实现每个频道独立存储自己的已删除消息,同时优化原有冗余的逻辑代码,修改后完整代码如下:
@bot.event async def on_message_delete(message): # 存储键改为(服务器ID, 频道ID)元组,实现频道级隔离 store_key = (message.guild.id, message.channel.id) if message.attachments: bob = message.attachments[0] bot.sniped_messages[store_key] = (bob.proxy_url, message.content, message.author, message.channel.name, message.created_at) else: bot.sniped_messages[store_key] = (None, message.content, message.author, message.channel.name, message.created_at) @bot.command(aliases=['s']) async def snipe(ctx): # 读取当前频道对应的存储记录 store_key = (ctx.guild.id, ctx.channel.id) if store_key not in bot.sniped_messages: await ctx.send("当前频道没有已删除的消息可捕获") return # 统一结构处理,不再需要嵌套异常捕获 bob_proxy_url, contents, author, channel_name, time = bot.sniped_messages[store_key] embed = discord.Embed(description=contents , color=discord.Color.purple(), timestamp=time) if bob_proxy_url: embed.set_image(url=bob_proxy_url) embed.set_author(name=f"{author.name}#{author.discriminator}", icon_url=author.avatar_url) embed.set_footer(text=f"Deleted in : #{channel_name}") await ctx.channel.send(embed=embed)
优化说明
- 统一了存储数据的结构,不管有没有附件都保持5个元素的元组,去掉了冗余的嵌套异常捕获逻辑
- 新增了无已删除消息时的友好提示,避免触发无意义的报错
- 频道级隔离后,只有当前执行命令的频道的已删除消息会被拉取,不会出现跨频道获取的问题
内容的提问来源于stack exchange,提问作者Džemal Imširović
相关产品推荐
相关产品推荐

