From 75c2a5644546adac6a7df2b2b0461519b9c1156b Mon Sep 17 00:00:00 2001 From: Sebastien Plante Date: Mon, 30 Jun 2025 23:55:36 -0400 Subject: [PATCH] first working version --- .gitignore | 1 + README.md | 44 ++++++++++++++++++ requirements.txt | 3 ++ src/bot.py | 115 +++++++++++++++++++++++++++++++++++++++++++++++ src/config.py | 7 +++ 5 files changed, 170 insertions(+) create mode 100644 .gitignore create mode 100644 requirements.txt create mode 100644 src/bot.py create mode 100644 src/config.py diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..2eea525 --- /dev/null +++ b/.gitignore @@ -0,0 +1 @@ +.env \ No newline at end of file diff --git a/README.md b/README.md index e69de29..1d23d5b 100644 --- a/README.md +++ b/README.md @@ -0,0 +1,44 @@ +# Discord Bot Hello + +Ce projet est un bot Discord simple qui répond "Hello World" lorsque l'utilisateur dit "Hello". + +## Prérequis + +Avant de commencer, assurez-vous d'avoir installé Python et pip sur votre machine. + +## Installation + +1. Clonez le dépôt ou téléchargez les fichiers du projet. +2. Naviguez dans le répertoire du projet. + + ```bash + cd discord-bot-hello + ``` + +3. Installez les dépendances nécessaires : + + ```bash + pip install -r requirements.txt + ``` + +4. Créez un fichier `.env` à la racine du projet et ajoutez votre token Discord : + + ```text + DISCORD_TOKEN=your_token_here + ``` + +## Exécution + +Pour exécuter le bot, utilisez la commande suivante : + +```bash +python src/bot.py +``` + +## Utilisation + +Une fois le bot en ligne, il répondra "Hello World" chaque fois qu'un utilisateur enverra "Hello" dans un canal où le bot a accès. + +## Aide + +Pour toute question ou problème, n'hésitez pas à ouvrir une issue dans le dépôt. diff --git a/requirements.txt b/requirements.txt new file mode 100644 index 0000000..d741a3e --- /dev/null +++ b/requirements.txt @@ -0,0 +1,3 @@ +discord.py +python-dotenv +pytz \ No newline at end of file diff --git a/src/bot.py b/src/bot.py new file mode 100644 index 0000000..86a6c38 --- /dev/null +++ b/src/bot.py @@ -0,0 +1,115 @@ +import os +import discord +import re +from datetime import datetime, timedelta +from dotenv import load_dotenv +import pytz + +load_dotenv() +TOKEN = os.getenv('DISCORD_TOKEN') + +intents = discord.Intents.default() +intents.message_content = True +client = discord.Client(intents=intents) + +# Dictionary to store the links between user messages and bot messages +user_to_bot_msg = {} + + +@client.event +async def on_ready(): + print(f'{client.user} has connected to Discord!') + + +def parse_time_message(content): + pattern = r'(\d{1,2}(?::|h)\d{2}(?:\s*(?:AM|PM|am|pm|Am|Pm|aM|pM))?)\s*([A-Za-z]{2,4})?' + content = re.sub(r'(\d{1,2})h(\d{2})', r'\1:\2', content) + match = re.search(pattern, content) + if not match: + return None, None + time_str = match.group(1).upper() + tz_str = match.group(2).upper() if match.group(2) else None + tz_map = { + "UTC": "UTC", + "CET": "Europe/Paris", + "CEST": "Europe/Paris", + "EST": "US/Eastern", + "EDT": "US/Eastern", + "CST": "US/Central", + "CDT": "US/Central", + "MST": "US/Mountain", + "MDT": "US/Mountain", + "PST": "US/Pacific", + "PDT": "US/Pacific", + } + if tz_str and tz_str.upper() in tz_map: + tzinfo = pytz.timezone(tz_map[tz_str.upper()]) + else: + tzinfo = datetime.now().astimezone().tzinfo + + now = datetime.now(tzinfo) + try: + try: + dt = datetime.strptime(time_str.strip(), "%I:%M %p") + except ValueError: + dt = datetime.strptime(time_str.strip(), "%H:%M") + dt = dt.replace(year=now.year, month=now.month, day=now.day) + dt = tzinfo.localize(dt) + if dt < now: + dt += timedelta(days=1) + timestamp = int(dt.timestamp()) + content = f"-# `{time_str} {tz_str}` is () in your timezone.\n-# *You can use this timestamp in your messages :* ` ()`" + return content, None + except Exception: + error = "Look like you are posting a time, if you can provide the time in a format like `8:30 PM CST` or `14:00 UTC`, I can help you convert it to a timestamp. Please try again." + return None, error + + +class DeleteButton(discord.ui.View): + def __init__(self): + super().__init__(timeout=None) + + @discord.ui.button(label="❌", style=discord.ButtonStyle.secondary, custom_id="delete_msg") + async def delete(self, interaction: discord.Interaction, button: discord.ui.Button): + if interaction.user == interaction.message.mentions[0] or interaction.user == interaction.message.author: + await interaction.message.delete() + else: + await interaction.response.send_message("-# Only the author can delete this message.", ephemeral=True) + + +@client.event +async def on_message(message): + if message.author == client.user: + return + + content, error = parse_time_message(message.content) + if content: + bot_msg = await message.reply(content) + user_to_bot_msg[message.id] = bot_msg.id + elif error: + bot_msg = await message.reply( + f"-# {message.author.mention} {error}", + view=DeleteButton() + ) + user_to_bot_msg[message.id] = bot_msg.id + + +@client.event +async def on_message_edit(before, after): + if after.author == client.user: + return + content, error = parse_time_message(after.content) + bot_msg_id = user_to_bot_msg.get(after.id) + channel = after.channel + if bot_msg_id: + try: + bot_msg = await channel.fetch_message(bot_msg_id) + quoted = f"> {after.content.replace('\n', '\n> ')}" + if content: + await bot_msg.edit(content=f"{quoted}\n{content}") + elif error: + await bot_msg.edit(content=f"{quoted}\n{after.author.mention} {error}", view=DeleteButton()) + except Exception: + pass + +client.run(TOKEN) diff --git a/src/config.py b/src/config.py new file mode 100644 index 0000000..2d625e9 --- /dev/null +++ b/src/config.py @@ -0,0 +1,7 @@ +# config.py +import os +from dotenv import load_dotenv + +load_dotenv() +TOKEN = os.getenv('DISCORD_TOKEN') +GUILD = os.getenv('DISCORD_GUILD') \ No newline at end of file