aboutsummaryrefslogtreecommitdiffstats
path: root/cogs/math_commands.py
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--cogs/math_commands.py83
1 files changed, 0 insertions, 83 deletions
diff --git a/cogs/math_commands.py b/cogs/math_commands.py
deleted file mode 100644
index e30c92b..0000000
--- a/cogs/math_commands.py
+++ /dev/null
@@ -1,83 +0,0 @@
1# This file is part of Senator Sperma
2# Licensed under the GPL-3.0 License
3# Copyright (C) 2026 Salmonik @ salmonik@tuta.io
4# https://codeberg.org/salmonik/senator-sperma
5
6import logging
7import asyncio
8import re
9
10from discord import ApplicationContext
11from discord.ext import commands
12
13logger = logging.getLogger(__name__)
14
15MATH_SANITIZE_PATTERN = re.compile(r'^[\d\s\+\-\*\/\^\%\(\)\.\,\=\\<\>\!\|\&\~\?\:\'\"\[\]\{\}a-zA-Z]+$')
16
17
18def sanitize_math_input(equation: str) -> str | None:
19 if not equation or len(equation) > 1000:
20 return None
21 equation = equation.strip()
22 if not equation:
23 return None
24 if not MATH_SANITIZE_PATTERN.match(equation):
25 return None
26 for char in equation:
27 if ord(char) < 32 or ord(char) > 126:
28 return None
29 if equation.count('(') != equation.count(')'):
30 return None
31 if equation.count('[') != equation.count(']'):
32 return None
33 if equation.count('{') != equation.count('}'):
34 return None
35 dangerous_patterns = [
36 r'eval', r'exec', r'__import__', r'os\.', r'sys\.',
37 r'subprocess', r'open(', r'file', r'shutil',
38 r'lambda:', r'compile', r'dir(', r'vars(',
39 r'\|\|', r'&&', r';', r'`', r'\$', r'\\n', r'\\r',
40 r'\x', r'\0', r'\a', r'\b', r'\f', r'\v',
41 ]
42 for pattern in dangerous_patterns:
43 if re.search(pattern, equation, re.IGNORECASE):
44 return None
45 return equation
46
47
48class Math(commands.Cog):
49 def __init__(self, bot):
50 self.bot = bot
51
52 @commands.slash_command(
53 name="math",
54 description="wrug szyskih matfisuf"
55 )
56 async def math(self, ctx: ApplicationContext, equation: str):
57 sanitized = sanitize_math_input(equation)
58 if sanitized is None:
59 await ctx.respond("Invalid equation. Only basic math expressions allowed.", ephemeral=True)
60 logger.warning(f"Math command rejected invalid input: {equation}")
61 return
62 try:
63 math_proc = await asyncio.create_subprocess_exec(
64 "qalc", "-e", sanitized,
65 stdout=asyncio.subprocess.PIPE,
66 stderr=asyncio.subprocess.PIPE
67 )
68 stdout, stderr = await math_proc.communicate()
69 if math_proc.returncode != 0:
70 error_output = stderr.decode('utf-8', errors='replace').strip()
71 await ctx.respond(f"Calculation error: {error_output}", ephemeral=True)
72 logger.error(f"qalc error: {error_output}")
73 return
74 result = stdout.decode('utf-8', errors='replace').strip()
75 await ctx.respond(f"{sanitized} = {result}")
76 logger.info(f"Math command executed: {sanitized}")
77 except Exception as e:
78 await ctx.respond(f"Error: {str(e)}", ephemeral=True)
79 logger.error(f"Error in math command: {e}", exc_info=True)
80
81
82def setup(bot):
83 bot.add_cog(Math(bot))