200 lines
7.5 KiB
Python
200 lines
7.5 KiB
Python
from .base import BaseModule, ENCODING
|
|
import random
|
|
import re
|
|
import json
|
|
from unidecode import unidecode
|
|
|
|
API_URL = "".join(
|
|
[
|
|
"https://discord.com/api/oauth2/authorize?",
|
|
"client_id=1110208055171367014&permissions=274877975552&scope=bot",
|
|
]
|
|
)
|
|
|
|
ABOUT = """
|
|
Ce bot a été développé par {user}
|
|
Code Source : https://gitlab.epicsparrow.com/Anselme/perefouras
|
|
Ajouter ce bot à votre serveur : {url}
|
|
"""
|
|
|
|
|
|
class FourasModule(BaseModule):
|
|
def load(self):
|
|
with open("riddles.txt", "r", encoding=ENCODING) as r_file:
|
|
self._client.riddles = r_file.read().split("\n\n")
|
|
with open("answers.txt", "r", encoding=ENCODING) as a_file:
|
|
self._client.answers = [line.strip() for line in a_file.readlines()]
|
|
print(f"Loaded {len(self._client.riddles)} riddles")
|
|
|
|
def save(self):
|
|
dump = {}
|
|
for key, value in self._client.ongoing_riddles.items():
|
|
dump_channel = dict(value)
|
|
dump_channel["message"] = dump_channel["message"].id
|
|
dump[key.id] = dump_channel
|
|
return dump
|
|
|
|
def new_riddle(self, channel, index):
|
|
current_riddle = dict(
|
|
index=index,
|
|
nbClues=-1,
|
|
riddle=self._client.riddles[index].strip(),
|
|
answer=self._client.answers[index],
|
|
)
|
|
self._client.ongoing_riddles[channel] = current_riddle
|
|
return self.format_message(current_riddle)
|
|
|
|
def finish_riddle(self, channel):
|
|
del self._client.ongoing_riddles[channel]
|
|
|
|
def clue_string(self, answer, nbClues):
|
|
finalString = "_"
|
|
for i in range(len(answer) - 1):
|
|
finalString += " _"
|
|
random.seed(hash(answer))
|
|
nbRevealed = 0
|
|
for i in range(nbClues):
|
|
id = random.randint(0, len(answer) - 1)
|
|
while finalString[id * 2] != "_":
|
|
id = random.randint(0, len(answer) - 1)
|
|
|
|
nbRevealed += 1
|
|
finalString = finalString[: id * 2] + answer[id] + finalString[id * 2 + 1 :]
|
|
|
|
if nbRevealed == len(answer):
|
|
return finalString
|
|
return finalString
|
|
|
|
def format_message(self, current_riddle):
|
|
nbClues = current_riddle["nbClues"]
|
|
answer = current_riddle["answer"]
|
|
|
|
formatted_riddle = "> " + current_riddle["riddle"].replace("\n", "\n> ")
|
|
formatted_riddle = formatted_riddle.replace("\r", "")
|
|
|
|
clue = ""
|
|
if nbClues > -1:
|
|
if nbClues >= len(answer):
|
|
clue = clue + "\nNon trouvée, la solution était : `{0}`".format(answer)
|
|
else:
|
|
clue = clue + "\nIndice : `{0}`".format(
|
|
self.clue_string(answer, nbClues)
|
|
)
|
|
|
|
if "solver" in current_riddle:
|
|
clue = clue + "\n{0} a trouvé la solution, qui était : `{1}`".format(
|
|
current_riddle["solver"].mention, answer
|
|
)
|
|
|
|
if clue:
|
|
return "Énigme {0}:\n{1}\n{2}".format(
|
|
current_riddle["index"] + 1, formatted_riddle, clue
|
|
)
|
|
else:
|
|
return "Énigme {0}:\n{1}".format(
|
|
current_riddle["index"] + 1, formatted_riddle
|
|
)
|
|
|
|
async def handle_message(self, message):
|
|
message_content = message.content.lower()
|
|
|
|
# command fouras
|
|
fouras_match = re.match(r"^fouras\s+(\d+)$", message_content)
|
|
if fouras_match:
|
|
index = int(fouras_match.group(1)) - 1
|
|
if index >= 0 and index < len(self._client.riddles):
|
|
if random.random() <= 0.03:
|
|
await message.channel.send("Non")
|
|
else:
|
|
await message.channel.send(self.new_riddle(message.channel, index))
|
|
else:
|
|
await message.channel.send(
|
|
"Numéro d'énigme invalide, merci de saisir un numéro ",
|
|
f"entre 1 et {len(self._client.riddles)}",
|
|
)
|
|
return
|
|
if message_content == "fouras":
|
|
if random.random() <= 0.03:
|
|
await message.channel.send("Non")
|
|
elif len(self._client.riddles) > 0:
|
|
index = random.randint(0, len(self._client.riddles) - 1)
|
|
await message.channel.send(self.new_riddle(message.channel, index))
|
|
return
|
|
|
|
# command reload
|
|
if message_content == "reload_riddles":
|
|
self.load()
|
|
await message.channel.send(
|
|
"Loaded {0} riddles".format(len(self._client.riddles))
|
|
)
|
|
return
|
|
|
|
if message_content == "about fouras":
|
|
author_user = await self._client.fetch_user(151626081458192384)
|
|
await message.channel.send(
|
|
ABOUT.format(user=author_user.mention, url=API_URL)
|
|
)
|
|
return
|
|
|
|
if message_content == "debug":
|
|
dump = {}
|
|
for key, value in self._client.ongoing_riddles.items():
|
|
dump_channel = dict(value)
|
|
dump_channel.pop("message", None)
|
|
dump_channel.pop("answer", None)
|
|
channel_name = await self.get_channel_name(key)
|
|
dump[channel_name] = dump_channel
|
|
await message.author.send(
|
|
"```json\n{0}```".format(json.dumps(dump, ensure_ascii=False, indent=4))
|
|
)
|
|
return
|
|
|
|
# if current channel has ongoing riddle
|
|
if message.channel in self._client.ongoing_riddles:
|
|
current_riddle = self._client.ongoing_riddles[message.channel]
|
|
|
|
if "message" in current_riddle:
|
|
answer = current_riddle["answer"]
|
|
if unidecode(answer.lower()) in unidecode(message_content):
|
|
current_riddle["solver"] = message.author
|
|
|
|
await message.channel.send(
|
|
f"Bravo {message.author.mention} ! ",
|
|
f"La réponse était bien `{answer}`.",
|
|
)
|
|
await current_riddle["message"].edit(
|
|
content=self.format_message(current_riddle)
|
|
)
|
|
self.finish_riddle(message.channel)
|
|
return
|
|
|
|
if (
|
|
message_content == "repete"
|
|
or message_content == "répète"
|
|
or message_content == "repeat"
|
|
):
|
|
current_riddle.pop("message")
|
|
await message.channel.send(self.format_message(current_riddle))
|
|
return
|
|
|
|
# Commande /clue : révèle une lettre au hasard de la réponse attendue
|
|
if (
|
|
message_content == "indice"
|
|
or message_content == "aide"
|
|
or message_content == "help"
|
|
or message_content == "clue"
|
|
):
|
|
nbClues = current_riddle["nbClues"] + 1
|
|
current_riddle["nbClues"] = nbClues
|
|
if nbClues >= len(answer):
|
|
reply = "Perdu ! La réponse était : `{0}`".format(answer)
|
|
await message.channel.send(reply)
|
|
# else:
|
|
# reply = "Indice : `{0}`".format(clue_string(answer, nbClues))
|
|
await current_riddle["message"].edit(
|
|
content=self.format_message(current_riddle)
|
|
)
|
|
if nbClues >= len(answer):
|
|
self.finish_riddle(message.channel)
|
|
return
|