lucandris
lucandris

Reputation: 46

How can I use advanced command handling in discord.py

So my bot is starting to have a lot of commands, and it's getting a bit messy on main.py. I know there's a way to store the commands in other files and then apply them to main.py when they are triggered on discord.js. Is it possible on discord.py as well?

Upvotes: 1

Views: 5757

Answers (1)

BenitzCoding
BenitzCoding

Reputation: 299

There are these things called "cogs", you can have a cog for events and some for other categories. Here's an example:

import discord
from discord.ext import commands, tasks

class ExampleCog(commands.Cog):
    def __init__(self, bot):
        self.bot = bot
    
    @commands.command() # You use commands.command() instead of bot.command()
    async def test(self, ctx): # you must always have self, if not it will not work.
        await ctx.send("**Test**")

    @commands.Cog.listener() # You use commands.Cog.listener() instead of bot.event
    async def on_ready(self):
        print("Test")

async def setup(bot):
    await bot.add_cog(ExampleCog(bot))

Whenever you use bot replace it with self.bot when you're using cogs. When you are using cogs, you need to have the cog files in a separate folder. You should make a folder called "./cogs/examplecog.py"

In your main bot file, you should have the code that is written below in order for the bot to read the cog files.

for file in os.listdir("./cogs"): # lists all the cog files inside the cog folder.
    if file.endswith(".py"): # It gets all the cogs that ends with a ".py".
        name = file[:-3] # It gets the name of the file removing the ".py"
        await bot.load_extension(f"cogs.{name}") # This loads the cog.

A benefit of having cogs is you don't need to restart the bot every time you want the new code to work, you just do !reload <cogname>, !unload <cogname>, or !load <cogname> and for those commands to work you need the code that is below.

Reload Cog Below

@bot.command()
@commands.is_owner()
async def reload(ctx, *, name: str):
    try:
        await bot.reload_extension(f"cogs.{name}")
    except Exception as e:
        return await ctx.send(e)
    await ctx.send(f'"**{name}**" Cog reloaded')

Unload Cog Below

@bot.command()
@commands.is_owner()
async def unload(ctx, *, name: str):
    try:
        await bot.unload_extension(f"cogs.{name}")
    except Exception as e:
        return await ctx.send(e)
    await ctx.send(f'"**{name}**" Cog unloaded')

Load Cog Below

@bot.command()
@commands.is_owner()
async def load(ctx, *, name: str):
    try:
        await bot.load_extension(f"cogs.{name}")
    except Exception as e:
        return await ctx.send(e)
    await ctx.send(f'"**{name}**" Cog loaded')

Note: The code might not work with slash commands to ensure that it does, use @bot.tree.app_command() instead of @bot.command() and @app_command() instead of @commands.command() for discord.py 2.0 to work normally with slash commands.

I hope you understood all of this. it took me about an hour to write this.

You can get more help from Senarc on this Discord Server

Finally, Have a nice day, and best of luck with your bot.

Upvotes: 5

Related Questions