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

Discord.py中如何检测用户是否屏蔽机器人并删除对应消息

Discord.py 检测用户屏蔽机器人的实现方案

首先明确核心前提:Discord 官方出于用户隐私规则,没有开放任何可以直接查询用户是否屏蔽机器人的API接口,不存在无副作用的前置检测手段,只能通过API异常捕获的方式间接判定,实现你需要的删消息逻辑。


可行实现逻辑

如果用户屏蔽了机器人,或是关闭了所在服务器的陌生人私信权限,机器人尝试向该用户发送私信时会直接抛出discord.Forbidden(403权限错误),这个特征可以作为判定依据。
为了避免检测操作骚扰正常用户,可以采用「发空测试私信→立刻撤回」的逻辑,未被屏蔽的用户完全感知不到检测操作。

前置要求:机器人必须拥有目标频道的管理消息权限,才能执行删除用户消息的操作;同时需要在开发者后台开启消息内容意图、服务器成员意图。

参考代码

import discord
from discord.ext import commands

# 配置必要权限
intents = discord.Intents.default()
intents.message_content = True
intents.members = True
bot = commands.Bot(command_prefix="!", intents=intents)

# 简单缓存检测结果,避免重复调用API触发限流,缓存有效期2小时
block_cache = {}

@bot.event
async def on_message(message):
    # 跳过机器人自身发送的消息
    if message.author.bot:
        return

    user_id = message.author.id
    # 优先读缓存
    if user_id in block_cache:
        is_blocked = block_cache[user_id]
    else:
        is_blocked = False
        try:
            # 发送空内容测试私信
            test_msg = await message.author.send("")
            # 发送成功立刻撤回,用户无感知
            await test_msg.delete()
        except discord.Forbidden:
            # 403错误即判定为无法向用户发私信(含被屏蔽、关闭私信两种情况)
            is_blocked = True
        # 写入缓存
        block_cache[user_id] = is_blocked

    # 判定为被屏蔽时删除对应消息
    if is_blocked:
        await message.delete()

    # 保持原有命令逻辑正常运行
    await bot.process_commands(message)

bot.run("你的机器人Token")

注意事项

  • 该方案无法区分「用户主动屏蔽机器人」和「用户关闭了服务器成员私信权限」两种情况,Discord返回的错误完全一致,没有进一步区分的手段。
  • 缓存机制是必须的,高频调用私信接口会触发Discord的API速率限制,严重时可能导致机器人被临时限制接口权限。
  • 不要在测试私信里携带任何实际内容,否则会对正常用户造成骚扰。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.31 00:12:40