discord.py中@tasks.loop异常及wait_until_ready使用疑问
Discord机器人Cog后台任务问题解答
问题1:注释代码报错原因
你注释里的代码在__init__方法中调用self.bot.loop.create_task(interval()),但__init__是同步方法,属于非异步上下文。此时Discord Bot还没完成异步初始化流程,loop属性无法在同步环境中被访问,这就是触发AttributeError的核心原因。
Discord.py的设计要求异步相关操作必须在异步上下文(比如异步函数、setup_hook这类异步初始化钩子)中执行,不能在同步的构造函数里直接操作事件循环。
问题2:为何await self.bot.wait_until_ready()必须放在loop函数内
- Cog初始化(
__init__执行)的时机,早于Bot完成登录、加载服务器/频道数据的时机。此时调用self.bot.get_channel(),Bot还没从Discord服务器拉取到频道信息,自然返回None。 await self.bot.wait_until_ready()会阻塞到Bot完成所有初始化步骤(包括登录成功、加载完所有缓存数据),这时候再调用get_channel才能拿到有效的频道对象。- 另外,把等待逻辑放在loop函数内,还能处理Bot重连的场景:如果Bot意外断开重连,再次执行loop时,等待操作会确保Bot重新初始化完成后再发送消息,避免再次出现
channel为None的问题。
附相关代码
class Task(Cog_Extension): def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) self.channel_id = xxx self.livingloop.start() @tasks.loop(seconds = 5) async def livingloop(self): await self.bot.wait_until_ready() channel = self.bot.get_channel(self.channel_id) print(channel) await channel.send("blabla") # async def interval(): # await self.bot.wait_until_ready() # self.channel = self.bot.get_channel(xxx) # while not self.bot.is_closed(): # await self.channel.send("blabla") # await asyncio.sleep(5) # self.bg_task = self.bot.loop.create_task(interval())
内容的提问来源于stack exchange,提问作者BARA
相关产品推荐
相关产品推荐

