当前位置: 首页 > 知识库问答 >
问题:

不和谐的许可制度。py机器人

姜兴业
2023-03-14

我正在使用discord制作discord机器人。py和asyncio。bot有像kickban这样的命令,这显然不应该对普通用户可用。

我想制作一个简单的系统,它将使用ctx检测用户角色的权限。消息编写以获取发送命令的用户。

我不希望bot检测到特定的角色名称,因为这些名称在不同的服务器上有所不同。我也不希望机器人有多个文件来保持简单。

我看到了不和谐。py文档和各种其他来源,但没有一个包含如何实现他们所讨论的各种方法的示例。

举个例子,这里有一个来自我的机器人的命令:

async def kick(ctx, userName: discord.User):
    if True: #ctx.message.author.Permissions.administrator
        await BSL.kick(userName)
    else:
        permission_error = str('Sorry ' + ctx.message.author + ' you do not have permissions to do that!')
        await BSL.send_message(ctx.message.channel, permission_error)

其中,如果还有语句是我试图自己做这件事。#ctx.message.author.Permissions.administrator被注释掉,因为它不起作用,并被True替换为测试目的。

提前感谢您的帮助和建议。

共有3个答案

柴赞
2023-03-14

找到公认答案的提示可能不起作用:

>

  • discord.py库的重写版本和预重写版本可能存在兼容性问题,这些版本保持不过时、不弃用且仍在使用。

    bot还应该检查自己的权限,以排除错误的一个原因。

    如果出现错误,或者bot本身的权限无效,bot应该说些什么,对吗?

    需要实现一些东西来防止机器人试图在DM或组上下文中运行此命令。它几乎总是会出错。

    我提出以下预重写的解决方案(假设您使用命令扩展):

    import discord
    from discord.ext import commands
    import time
    @bot.command(pass_context=True,description="Kicks the given member. Please ensure both the bot and the command invoker have the permission 'Kick Members' before running this command.")
    async def kick(ctx, target:discord.Member):
        """(GUILD ONLY) Boot someone outta the server. See 's!kick' for more."""
        if not str(ctx.message.channel).startswith("Direct Message with "):
            msg=await bot.say("Checking perms...")
            time.sleep(0.5)
            if ctx.message.server.me.server_permissions.kick_members:
                if ctx.message.author.server_permissions.kick_members:
                    await bot.edit_message(msg,new_content="All permissions valid, checking issues with target...")
                    time.sleep(0.5)
                    if target==ctx.message.server.owner:
                        await bot.edit_message(msg, new_content="All permissions are correct, but you're attempting to kick the server owner, whom you can't kick no matter how hard you try. Whoops!")
                    else:
                        if target==ctx.message.server.me:
                            await bot.edit_message(msg, new_content="Whoops! All permissions are corrent, but you just tried to make me kick myself, which is not possible. Perhaps you meant someone else, not poor me?")
                        else:
                            await bot.edit_message(msg, new_content="All permissions correct, and no issues with target being self or server owner, attempting to kick.")
                            time.sleep(2)
                            try:
                                await bot.kick(target)
                                await bot.edit_message(msg, ":boom: BAM! ***kicc'd***")
                            except Exception:
                                await bot.edit_message(msg, new_content="I was unable to kick the passed member. The member may have a higher role than me, I may have crashed into a rate-limit, or an unknown error may have occured. In that case, try again.")
                else:
                    await bot.edit_message(msg, new_content="I've the correct permissions, {}, but you do not. Perhaps ask for them?").format(ctx.message.author.mention)
            else:
                await bot.edit_message(msg, new_content="I'm just a poor bot with no permissions. Could you kindly grant me the permission `Kick Members`? Thanks! :slight_smile:")
        else:
            await bot.say("'Tis a DM! This command is for servers only... try this again in a server maybe? :slight_smile:")
    

  • 申屠泉
    2023-03-14

    你也可以使用装饰器。

    @bot.command(name = "Kick")
    @bot.has_permissions(kick_user = True)
    @bot.bot_has_permissions(kick_user = True)
    async def _kick(ctx, member: Member):
        #Do stuff...
    

    检查用户和bot权限的优势意味着更容易处理来自提供有用的“权限不足”错误消息的错误。

    何高歌
    2023-03-14

    权限是类的名称。要获取消息作者权限,您应该访问作者的guild\u permissions属性。

    if ctx.message.author.guild_permissions.administrator:
     # you could also use guild_permissions.kick_members
    

    更新:

    验证调用命令的人的权限的更好方法是使用命令扩展的检查功能,特别是has_permissions检查。例如,如果您想只向具有manage_roles权限或ban_members权限的人打开您的命令,您可以这样写您的命令:

    from discord import Member
    from discord.ext.commands import has_permissions, MissingPermissions
    
    @bot.command(name="kick", pass_context=True)
    @has_permissions(manage_roles=True, ban_members=True)
    async def _kick(ctx, member: Member):
        await bot.kick(member)
    
    @_kick.error
    async def kick_error(ctx, error):
        if isinstance(error, MissingPermissions):
            text = "Sorry {}, you do not have permissions to do that!".format(ctx.message.author)
            await bot.send_message(ctx.message.channel, text)
    
     类似资料:
    • 我试图让我的自我机器人加入服务器。我知道self-bots反对discordtos,但我想学习一些新的东西。 这是我尝试过的命令: 错误:

    • 我试图在重写discord.py不和谐的自我机器人,它给了我这个错误: 这是我的代码:

    • 我已经创建了一个bot,它现在在我的discord服务器中,使用下面的代码。 我的问题是,一旦我在与bot不和谐的聊天中,我如何调用命令让bot运行代码,为用户列表收集csv?我不确定如何调用机器人,一旦它在聊天/服务器中获得列表。

    • 我使用repl。它让我的不和机器人。我使用Python并遵循本教程: https://www.youtube.com/watch?v=SPTfmiYiuok 这是我的代码:

    • 当我在discord内部运行以下脚本(“cmd中的node musicbot.js”)和“!play ytlink”时,bot加入语音通道,并在控制台中记录命令和链接。然而,音乐并没有开始播放。我安装了ffmpeg、ytdl核心和discord。js。 有人能帮我吗?我不知道是哪一部分搞砸了。

    • 当有人加入语音频道时,如何制作一个标记为@角色的discord机器人?示例:@role{user}已加入