我写了一个相当大的 Discord 机器人。它有超过 1000 行代码。当我在 Youtube 和这里研究如何做到这一点时,似乎没有任何效果。我想知道是否有人可以解释如何正确使用齿轮,可能用照片示例。我可以展示我需要哪些代码来帮助您理解我想要什么。
一个例子是,我想将所有 mod 命令放在一个单独的文件中,这样它更干净、更有组织。那么,我该怎么做呢?这是我的代码示例:
Mod 命令我想使用 cog 移动到单独的文件
#kick Command
@bot.command(pass_context=True)
@commands.has_role("BotUser")
async def kick(ctx, user: discord.Member):
await bot.say(":boot:{} has been kicked from the server... Too bad...".format(user.name))
await bot.kick(user)
await bot.delete_message(ctx.message)
#Ban Command
@bot.command(pass_context=True)
@commands.has_role("BotUser")
async def ban(ctx, user: discord.Member):
await bot.say(":rofl: {} has been banned until further notice... Sucks to Suck")
await bot.ban(user)
await bot.delete_message(ctx.message)
#Clear command (Can only clear messages over 14 days old!)
@bot.command(pass_context=True)
@commands.has_role("BotUser")
async def clear(ctx, amount=100):
channel = ctx.message.channel
messages = []
async for message in bot.logs_from(channel, limit=int(amount) + 1):
messages.append(message)
await bot.delete_messages(messages)
await bot.delete_message(ctx.message)
目前我拥有的进口
import discord
from discord.ext import commands
from discord.ext.commands import Bot
import asyncio
import json
import os
前缀和目录
bot = commands.Bot(command_prefix='.')
bot.remove_command('help')
players = {}
queues = {}
os.chdir(r"C:\Users\anakr\Documents\DiscordBots\Bot Test")
调用令牌ID - 令牌ID在上面,未显示:
bot.run(TOKEN)
我不确定如何完全启动一个齿轮,还要导入什么,如何调用文件。我很了解 Java,但我正在尝试通过 Discord 来提高我的 Python 技能。
下面是为旧的 0.16 版本编写的,该版本没有很好的 cogs 文档。新的1.0版本有很好的文档,并且完全改变了cogs的结构。如果您使用的是现代版本的 discord.py,您应该查阅 官方文档。
每个齿轮都有两部分:一个类和一个
setup
函数。几乎所有 setup
功能看起来都一样:
def setup(bot):
bot.add_cog(Cog(bot))
其中
Cog
是齿轮类别。
cog 类包含我们所有的命令和事件作为方法。
要将机器人更改为齿轮,您需要执行四个主要转换:
将
bot.command
替换为 commands.command
(commands
为 from discord.ext import commands
)更改函数的签名以在开头包含
self
,因为所有命令和事件现在都是 cog 类的方法将所有对
bot
的引用更改为引用 self.bot
删除所有
bot.event
装饰器。来自您的 cog 的事件侦听器仅以名称注册还有一些陷阱:
从齿轮中的任何
await bot.process_commands(message)
事件中删除 on_message
。对于任何消息,只应等待一次。默认的 on_message
已经为你做到了这一点。通过 cog 注册事件不会从主文件或其他 cog 中删除与该事件相关的其他回调。这意味着您的机器人可以多次响应
on_member_join
事件,例如,如果您在多个位置定义了该事件的行为。假设您有以下discord.py机器人,
bot.py
在目录src
中:
from discord.ext import commands
bot = commands.Bot(command_prefix='!')
@bot.command(pass_context=True)
@commands.has_role("Mod")
async def acommand(ctx, argument):
await bot.say("Stuff")
@bot.event
async def on_message(message):
print(message.content)
await bot.process_commands(message)
bot.run("token")
然后您将该功能分解为一个齿轮
src/cogs/maincog.py
from discord.ext import commands
class MainCog:
def __init__(self, bot):
self.bot = bot
@commands.command(pass_context=True)
@commands.has_role("Mod")
async def acommand(self, ctx, argument):
await self.bot.say("Stuff")
async def on_message(self, message):
print(message.content)
def setup(bot):
bot.add_cog(MainCog(bot))
你的
bot.py
文件看起来像
from discord.ext import commands
bot = commands.Bot(command_prefix='!')
bot.load_extension("cogs.maincog")
bot.run("token")
请注意,要在
cogs/maincog.py
加载扩展,我们使用 load_extension("cogs.maincog")
。
Cogs 还允许您定义一些特殊的方法。其中大部分仅在 discord.py-rewrite 中可用,并记录在 here。
__global_check
(以前称为 __check
)在每个命令之前运行,并且必须返回 True
才能继续执行该命令。__local_check
仅在来自该齿轮的命令之前运行。__global_check_once
我相信这与__global_check
类似,只是在子命令的情况下它只检查一次。我还没用过这么多。__unload
您可以通过卸载扩展程序然后重新加载来实时刷新您的机器人,从而允许您更新您的齿轮而无需使您的机器人离线。当您卸载扩展程序或当您的机器人停止运行时,会调用此方法,以防您需要进行清理。__before_invoke
和 __after_invoke
分别在该齿轮的每个命令之前和之后运行。__error
是来自该齿轮的命令的错误处理程序。基本的齿轮模板如下所示:
import discord
import asyncio
from discord.ext import commands
class cog_name(commands.Cog):
def __init__(self, bot):
self.bot = bot
def setup(bot):
bot.add_cog(cog_name(bot))
要将此齿轮添加到您的机器人,请在主文件中添加以下内容:
client.load_extension('script_name')
如果 cog 脚本位于文件夹内,请添加
client.load_extension('folder_name.script_name')
如果它是一个审核齿轮,您可以按照提供的以下代码进行操作: 主文件:
import discord
from discord.ext import commands
import moderation
bot = commands.Bot(command_prefix=your_prefix)
async def load():
cogs = [moderation]
for i in range(len(cogs)):
cogs[i].setup(bot)
@bot.event
async def on_ready():
print("Bot is ready!")
await load()
print("Cogs synced!")
bot.run(your token)
审核文件:
from discord.ext import commands
import discord
from discord import app_commands
class moderation(commands.Cog):
def __init__(self,bot):
self.bot:commands.Bot = bot
@app_commands.command()
@app_commands.default_permissions(ban_members=True)
async def ban(self,interaction:discord.Interaction,member:discord.Member,*,reason:str):
await member.ban()
await interaction.response.send_message(f"{member} was banned!")
@app_commands.command()
@app_commands.default_permissions(ban_members=True)
async def kick(self,interaction:discord.Interaction,member:discord.Member,*,reason:str):
await member.kick()
await interaction.response.send_message(f"{member} was kicked!")
@app_commands.command()
async def clear(self,interaction:discord.Interaction, amount:int):
await interaction.channel.purge(limit=amount)
async def setup(bot):
await bot.add_cog(moderation(bot))