Discord.py协程未等待错误:无法通过邀请链接获取服务器名称
问题:通过Discord邀请链接获取服务器名称时的异步错误
我想写代码通过Discord服务器邀请链接获取服务器名称,但一直碰到coroutine was never awaited错误。我试着在client.fetch_invite(link).guild.name前加await但没用,也搞不懂异步机制。按照建议修改后又出现了AttributeError,相关代码和报错信息如下:
原代码
import discord from discord.ext import commands intents = discord.Intents.default() intents.message_content = True client = discord.Client(intents=intents) async def get_invite_name(link): name = await client.fetch_invite(link).guild.name return name print(get_invite_name('https://discord.com/invite/veefriends'))
修改后的报错信息
File "~/DLG/sandbox.py", line 14, in <module> print(asyncio.run(get_invite_name('https://discord.com/invite/veefriends'))) File "/usr/lib/python3.10/asyncio/runners.py", line 44, in run return loop.run_until_complete(main) File "/usr/lib/python3.10/asyncio/base_events.py", line 646, in run_until_complete return future.result() File "~/DLG/sandbox.py", line 12, in get_invite_name return await invite.guild.name AttributeError: 'coroutine' object has no attribute 'guild' sys:1: RuntimeWarning: coroutine 'Client.fetch_invite' was never awaited
错误原因分析
- 异步调用逻辑错误:
client.fetch_invite()是异步函数,必须先通过await执行它拿到真实的邀请对象,才能访问.guild.name属性。你之前的写法await client.fetch_invite(link).guild.name是错的——相当于先去访问未执行的协程对象的.guild属性,而非等待协程完成后再取属性。 - 客户端未正确初始化:Discord的
Client必须先登录(连接到Discord网关)才能调用fetch_invite接口,否则无法正常获取数据。
修正后的代码
import discord import asyncio intents = discord.Intents.default() intents.message_content = True client = discord.Client(intents=intents) async def get_invite_name(link): # 先等待fetch_invite执行完成,拿到Invite实例 invite = await client.fetch_invite(link) # 从实例中提取服务器名称 return invite.guild.name async def main(): # 替换成你自己的Discord Bot Token await client.login('YOUR_BOT_TOKEN_HERE') guild_name = await get_invite_name('https://discord.com/invite/veefriends') print(guild_name) await client.close() if __name__ == "__main__": asyncio.run(main())
关键注意点
- 异步函数的调用必须分步:先
await异步方法拿到结果对象,再访问对象的属性,不能链式调用时直接给整个表达式加await。 - 必须使用有效的Bot Token登录,Token需要在Discord开发者平台创建Bot后获取。
- 所有异步代码要放在异步上下文里执行,用
asyncio.run()启动主协程是最直接的方式。
内容的提问来源于stack exchange,提问作者Pranav Ammini
相关产品推荐
相关产品推荐

