diff --git a/.vscode/PythonImportHelper-v2-Completion.json b/.vscode/PythonImportHelper-v2-Completion.json index 8812d07..f5f01e0 100644 --- a/.vscode/PythonImportHelper-v2-Completion.json +++ b/.vscode/PythonImportHelper-v2-Completion.json @@ -82,6 +82,15 @@ "detail": "io", "documentation": {} }, + { + "label": "os", + "kind": 6, + "isExtraImport": true, + "importPath": "os", + "description": "os", + "detail": "os", + "documentation": {} + }, { "label": "subprocess", "kind": 6, @@ -143,15 +152,6 @@ "detail": "dotenv", "documentation": {} }, - { - "label": "os", - "kind": 6, - "isExtraImport": true, - "importPath": "os", - "description": "os", - "detail": "os", - "documentation": {} - }, { "label": "logging", "kind": 6, @@ -166,7 +166,7 @@ "kind": 6, "importPath": "cogs.chance", "description": "cogs.chance", - "peekOfCode": "class Fun(commands.Cog):\n def __init__(self, bot):\n self.bot = bot\n @commands.command()\n async def coin(self, ctx):\n result = random.choice(['🪙 Heads', '🪙 Tails'])\n await ctx.reply(f'{result}')\n @commands.command()\n async def dice(self, ctx):\n result = random.randint(1, 6)", + "peekOfCode": "class Fun(commands.Cog):\n def __init__(self, bot):\n self.bot = bot\n # this command lists all the fun commands, not an actualy fun command##\n @commands.command()\n async def fun(self, ctx):\n fun_commands = [f'!{cmd.name}' for cmd in self.get_commands() if cmd.name != 'fun']\n await ctx.reply('\\n'.join(sorted(fun_commands)))\n ######################################################################\n @commands.command()", "detail": "cogs.chance", "documentation": {} }, @@ -175,7 +175,7 @@ "kind": 6, "importPath": "cogs.copypasta", "description": "cogs.copypasta", - "peekOfCode": "class Copypasta(commands.Cog):\n def __init__(self, bot):\n self.bot = bot\n @commands.command()\n async def yuukapasta(self, ctx):\n pasta = (\"\"\"Since Yuuka is the paragon of human virtue without equal past or present, she is most resplendent in love, tributes and accolades. Waking or sleeping, I must not forget Yuuka’s great boon and in order to return her favour by day and by night, I should only think of fulfilling my loyalty.\nWho is Yuuka?\nFor the blind, she is their vision. For the deaf, she is their music. For the mute, she is their voice. For the anosmiac, she is their aroma. For the numb, she is their feeling. For the atrophied, she is their muscle.\nFor the starved, she is their sustenance. For the thirsty, she is their water. For the exhausted, she is their energy.\nFor the depressed, she is their happiness. For the disillusioned, she is their hope. For the pessimistic, she is their optimism.", + "peekOfCode": "class Copypasta(commands.Cog):\n def __init__(self, bot):\n self.bot = bot\n # this command lists all the copypasta commands, not an actualy copypasta command##\n @commands.command()\n async def copypasta(self, ctx):\n pasta_commands = [f'!{cmd.name}' for cmd in self.get_commands() if cmd.name != 'copypasta']\n await ctx.reply('\\n'.join(sorted(pasta_commands)))\n ######################################################################\n @commands.command()", "detail": "cogs.copypasta", "documentation": {} }, @@ -193,7 +193,7 @@ "kind": 6, "importPath": "cogs.gifs", "description": "cogs.gifs", - "peekOfCode": "class Gifs(commands.Cog):\n def __init__(self, bot):\n self.bot = bot\n #this command lists all the gif commands, not an actualy gif command##\n @commands.command()\n async def gifs(self, ctx):\n gif_commands = [f'!{cmd.name}' for cmd in self.get_commands()]\n await ctx.reply('\\n'.join(gif_commands))\n ######################################################################\n @commands.command()", + "peekOfCode": "class Gifs(commands.Cog):\n def __init__(self, bot):\n self.bot = bot\n self._load_gif_commands()\n def _load_gif_commands(self):\n if not os.path.exists('gifs'):\n return\n for filename in os.listdir('gifs'):\n if filename.endswith('.gif'):\n name = filename[:-4] # strip .gif", "detail": "cogs.gifs", "documentation": {} }, diff --git a/README.md b/README.md new file mode 100644 index 0000000..378f3cd --- /dev/null +++ b/README.md @@ -0,0 +1,24 @@ +# yuuka + +Personal Discord bot running on my Arch Linux laptop. Named after Hayase Yuuka. + +## Features + +- Music playback via Lavalink — YouTube search, URLs, playlists, queue management +- Live system monitoring — CPU, RAM, temps, disk, top processes, fastfetch +- Fun commands — dice, coinflip, aura meter, rank, gifs, copypastas + +## Stack + +- Python + discord.py +- Wavelink + Lavalink for audio +- psutil + lm-sensors for sysinfo +- Hosted on an Acer Nitro AN515-51 running Arch Linux +- Runs as a systemd service, updated via git pull over SSH + +## Commands + +- `!music` — full music command list +- `!sysinfo` — full sysinfo command list +- `!gifs` — full gif list +- `!help` — everything else \ No newline at end of file diff --git a/cogs/chance.py b/cogs/chance.py index 9a1dd49..6b22c75 100644 --- a/cogs/chance.py +++ b/cogs/chance.py @@ -6,6 +6,13 @@ class Fun(commands.Cog): def __init__(self, bot): self.bot = bot + # this command lists all the fun commands, not an actualy fun command## + @commands.command() + async def fun(self, ctx): + fun_commands = [f'!{cmd.name}' for cmd in self.get_commands() if cmd.name != 'fun'] + await ctx.reply('\n'.join(sorted(fun_commands))) + ###################################################################### + @commands.command() async def coin(self, ctx): result = random.choice(['🪙 Heads', '🪙 Tails']) diff --git a/cogs/copypasta.py b/cogs/copypasta.py index d70cdc7..787e826 100644 --- a/cogs/copypasta.py +++ b/cogs/copypasta.py @@ -7,6 +7,13 @@ class Copypasta(commands.Cog): def __init__(self, bot): self.bot = bot + # this command lists all the copypasta commands, not an actualy copypasta command## + @commands.command() + async def copypasta(self, ctx): + pasta_commands = [f'!{cmd.name}' for cmd in self.get_commands() if cmd.name != 'copypasta'] + await ctx.reply('\n'.join(sorted(pasta_commands))) + ###################################################################### + @commands.command() async def yuukapasta(self, ctx): pasta = ("""Since Yuuka is the paragon of human virtue without equal past or present, she is most resplendent in love, tributes and accolades. Waking or sleeping, I must not forget Yuuka’s great boon and in order to return her favour by day and by night, I should only think of fulfilling my loyalty. diff --git a/cogs/gifs.py b/cogs/gifs.py index cf6970d..56f13e4 100644 --- a/cogs/gifs.py +++ b/cogs/gifs.py @@ -1,53 +1,32 @@ # this is where gif commands live import discord +import os from discord.ext import commands class Gifs(commands.Cog): def __init__(self, bot): self.bot = bot + self._load_gif_commands() + + def _load_gif_commands(self): + if not os.path.exists('gifs'): + return + for filename in os.listdir('gifs'): + if filename.endswith('.gif'): + name = filename[:-4] # strip .gif + self._make_command(name) + + def _make_command(self, name: str): + async def gif_command(self, ctx): + await ctx.reply(file=discord.File(f'gifs/{name}.gif')) + gif_command.__name__ = name + cmd = commands.command(name=name)(gif_command) + self.add_command(cmd) - #this command lists all the gif commands, not an actualy gif command## @commands.command() async def gifs(self, ctx): - gif_commands = [f'!{cmd.name}' for cmd in self.get_commands()] - await ctx.reply('\n'.join(gif_commands)) - ###################################################################### - - @commands.command() - async def czech(self, ctx): - await ctx.reply(file=discord.File('gifs/czech.gif')) - - @commands.command() - async def dogshit(self, ctx): - await ctx.reply(file=discord.File('gifs/dogshit.gif')) - - @commands.command() - async def how(self, ctx): - await ctx.reply(file=discord.File('gifs/how.gif')) - - @commands.command() - async def peak(self, ctx): - await ctx.reply(file=discord.File('gifs/peak.gif')) - - @commands.command() - async def please(self, ctx): - await ctx.reply(file=discord.File('gifs/please.gif')) - - @commands.command() - async def shoo(self, ctx): - await ctx.reply(file=discord.File('gifs/shoo.gif')) - - @commands.command() - async def spell(self, ctx): - await ctx.reply(file=discord.File('gifs/spell.gif')) - - @commands.command() - async def tired(self, ctx): - await ctx.reply(file=discord.File('gifs/tired.gif')) - - @commands.command() - async def touch(self, ctx): - await ctx.reply(file=discord.File('gifs/touch.gif')) + gif_commands = [f'!{cmd.name}' for cmd in self.get_commands() if cmd.name != 'gifs'] + await ctx.reply('\n'.join(sorted(gif_commands))) async def setup(bot): await bot.add_cog(Gifs(bot)) \ No newline at end of file