""" Groovy-Zilean Bot Class Main bot implementation with cog loading and background tasks """ from typing import Any from discord.ext import commands from discord.ext import tasks from cogs.music.main import music from help import GroovyHelp # List of cogs to load on startup cogs: list[type[commands.Cog]] = [ music, GroovyHelp ] class Groovy(commands.Bot): """Custom bot class with automatic cog loading and inactivity checking""" def __init__(self, *args: Any, **kwargs: Any) -> None: # We force help_command to None because we are using a custom Cog for it # But we pass all other args (like command_prefix) to the parent super().__init__(*args, help_command=None, **kwargs) async def on_ready(self) -> None: import config # Imported here to avoid circular dependencies if any # Set status await self.change_presence(activity=config.get_status()) # Load cogs print(f"Loading {len(cogs)} cogs...") for cog in cogs: try: print(f"Attempting to load: {cog.__name__}") await self.add_cog(cog(self)) print(f"✅ Loaded {cog.__name__}") except Exception as e: print(f"❌ Failed to load {cog.__name__}: {e}") import traceback traceback.print_exc() # Sync slash commands with Discord print("🔄 Syncing slash commands...") try: synced = await self.tree.sync() print(f"✅ Synced {len(synced)} slash command(s)") except Exception as e: print(f"❌ Failed to sync commands: {e}") # Start inactivity checker if not self.inactivity_checker.is_running(): self.inactivity_checker.start() print(f"✅ {self.user} is ready and online!") @tasks.loop(seconds=30) async def inactivity_checker(self) -> None: """Check for inactive voice connections every 30 seconds""" from cogs.music import util await util.check_inactivity(self) @inactivity_checker.before_loop async def before_inactivity_checker(self) -> None: """Wait for bot to be ready before starting inactivity checker""" await self.wait_until_ready()