You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

discord.py代码AttributeError异常捕获位置及处理方案咨询

问题原因

你的现有AttributeError捕获逻辑仅能覆盖最外层try代码块内的异常,本次报错触发于except Forbidden分支内部:
当self.client.get_channel(self.grab_log_id(channel))返回None(常见原因是日志频道ID无效、机器人未被授予该频道的访问权限)时,channel1变量为空值。如果此时try块内的踢人操作先触发了Forbidden异常,进入权限提示分支后调用channel1.send()就会抛出'NoneType' object has no attribute 'send'错误,而这个调用不在最外层try的覆盖范围内,所以原捕获逻辑无法生效。

修复方案

推荐提前对channel1合法性做校验,同时调整异常捕获的覆盖范围,完整实现代码如下,已包含打印"F"、写入JSON、日志输出逻辑:

import json
import datetime

try:
    channel1 = self.client.get_channel(self.grab_log_id(channel))
    # 提前校验channel1是否为空,避免后续多处调用报错
    if not channel1:
        raise AttributeError("日志频道获取失败")
    
    await channel.guild.kick(i.user, reason="Assistant Anti: Deleting Channels")
    lel = discord.Embed(title='Action Assisted', description=f'**Target** : {i.user} | `{i.user.id}` \n **Action** : Kicked; Deleted Channel')
    await channel1.send(embed=lel)
    return

except Forbidden:
    emd=discord.Embed(title="⚠️ Warning ⚠️", description="I am missing the necessary permissions to perform actions. \n Check if: \n   - I am above __ALL__ users. \n   - I have __Administrator__ permission.")
    # 这里的channel1已经提前做了非空校验,不会再触发AttributeError
    await channel1.send(f"{channel.guild.owner.mention}")
    await channel1.send(embed=emd)

except AttributeError:
    print("F")
    # 写入异常频道ID到JSON文件
    log_data = {
        "invalid_channel_id": self.grab_log_id(channel),
        "guild_id": channel.guild.id,
        "error_time": datetime.datetime.now().isoformat()
    }
    try:
        with open("channel_error_log.json", "r+", encoding="utf-8") as f:
            try:
                exist_data = json.load(f)
            except json.JSONDecodeError:
                exist_data = []
            exist_data.append(log_data)
            f.seek(0)
            json.dump(exist_data, f, indent=2, ensure_ascii=False)
    except FileNotFoundError:
        # 文件不存在时新建写入
        with open("channel_error_log.json", "w", encoding="utf-8") as f:
            json.dump([log_data], f, indent=2, ensure_ascii=False)
    # 本地控制台日志输出
    print(f"日志频道获取异常,已记录错误信息:{log_data}")

如果不需要提前校验,也可以给except Forbidden分支内部的调用单独嵌套try-except逻辑,效果一致。

内容的提问来源于stack exchange,提问作者tammy copper

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.09 22:54:04