2019-10-06 23:49:00 +02:00
|
|
|
import json
|
2019-10-06 01:49:30 +02:00
|
|
|
from typing import Union
|
|
|
|
|
|
|
|
import discord
|
|
|
|
import bcrypt
|
2019-09-28 01:39:45 +02:00
|
|
|
from discord.ext import commands
|
|
|
|
|
|
|
|
from bot import TuxBot
|
|
|
|
from .utils.lang import Texts
|
2019-10-06 01:49:30 +02:00
|
|
|
from .utils.models import Poll
|
|
|
|
from .utils import emotes as utils_emotes
|
2019-09-28 01:39:45 +02:00
|
|
|
|
|
|
|
|
2019-10-06 01:49:30 +02:00
|
|
|
class Polls(commands.Cog):
|
2019-09-28 01:39:45 +02:00
|
|
|
|
|
|
|
def __init__(self, bot: TuxBot):
|
|
|
|
self.bot = bot
|
|
|
|
|
2019-10-06 01:49:30 +02:00
|
|
|
def get_poll(self, pld) -> Union[bool, Poll]:
|
|
|
|
if pld.user_id != self.bot.user.id:
|
2019-10-06 23:49:00 +02:00
|
|
|
poll = self.bot.database.session \
|
2019-10-06 01:49:30 +02:00
|
|
|
.query(Poll) \
|
2019-10-06 23:49:00 +02:00
|
|
|
.filter(Poll.message_id == pld.message_id)
|
2019-10-06 01:49:30 +02:00
|
|
|
|
2019-10-06 23:49:00 +02:00
|
|
|
if poll.count() != 0:
|
|
|
|
poll = poll.one()
|
2019-10-06 01:49:30 +02:00
|
|
|
emotes = utils_emotes.get(len(poll.responses))
|
|
|
|
|
|
|
|
if pld.emoji.name in emotes:
|
|
|
|
return poll
|
|
|
|
|
|
|
|
return False
|
|
|
|
|
|
|
|
async def remove_reaction(self, pld):
|
2019-10-06 23:49:00 +02:00
|
|
|
channel: discord.TextChannel = self.bot.get_channel(pld.channel_id)
|
|
|
|
message: discord.Message = await channel.fetch_message(pld.message_id)
|
2019-10-06 01:49:30 +02:00
|
|
|
user: discord.User = await self.bot.fetch_user(pld.user_id)
|
|
|
|
|
|
|
|
await message.remove_reaction(pld.emoji.name, user)
|
|
|
|
|
2019-10-06 23:49:00 +02:00
|
|
|
async def update_poll(self, poll_id: int):
|
|
|
|
poll = self.bot.database.session \
|
|
|
|
.query(Poll) \
|
|
|
|
.filter(Poll.id == poll_id) \
|
|
|
|
.one()
|
|
|
|
channel: discord.TextChannel = self.bot.get_channel(poll.channel_id)
|
|
|
|
message: discord.Message = await channel.fetch_message(poll.message_id)
|
|
|
|
|
|
|
|
content = json.loads(poll.content) \
|
|
|
|
if isinstance(poll.content, str) \
|
|
|
|
else poll.content
|
|
|
|
responses = json.loads(poll.responses) \
|
|
|
|
if isinstance(poll.responses, str) \
|
|
|
|
else poll.responses
|
|
|
|
|
|
|
|
for i, field in enumerate(content.get('fields')):
|
|
|
|
responders = len(responses.get(str(i + 1)))
|
|
|
|
if responders <= 1:
|
|
|
|
field['value'] = f"**{responders}** vote"
|
|
|
|
else:
|
|
|
|
field['value'] = f"**{responders}** votes"
|
|
|
|
|
|
|
|
e = discord.Embed(description=content.get('description'))
|
|
|
|
e.set_author(
|
|
|
|
name=content.get('author').get('name'),
|
|
|
|
icon_url=content.get('author').get('icon_url')
|
|
|
|
)
|
|
|
|
for field in content.get('fields'):
|
|
|
|
e.add_field(
|
|
|
|
name=field.get('name'),
|
|
|
|
value=field.get('value'),
|
|
|
|
inline=True
|
|
|
|
)
|
|
|
|
e.set_footer(text=content.get('footer').get('text'))
|
|
|
|
|
|
|
|
await message.edit(embed=e)
|
|
|
|
|
|
|
|
poll.content = json.dumps(content)
|
|
|
|
self.bot.database.session.commit()
|
|
|
|
|
2019-10-06 01:49:30 +02:00
|
|
|
@commands.Cog.listener()
|
|
|
|
async def on_raw_reaction_add(self, pld: discord.RawReactionActionEvent):
|
|
|
|
poll = self.get_poll(pld)
|
|
|
|
|
|
|
|
if poll:
|
|
|
|
if poll.is_anonymous:
|
|
|
|
await self.remove_reaction(pld)
|
|
|
|
|
|
|
|
user_id = str(pld.user_id).encode()
|
|
|
|
|
|
|
|
choice = utils_emotes.get_index(pld.emoji.name) + 1
|
2019-10-06 23:49:00 +02:00
|
|
|
responses = json.loads(poll.responses) \
|
|
|
|
if isinstance(poll.responses, str) \
|
|
|
|
else poll.responses
|
2019-10-06 01:49:30 +02:00
|
|
|
|
2019-10-06 23:49:00 +02:00
|
|
|
if not responses.get(str(choice)):
|
|
|
|
print(97)
|
2019-10-06 01:49:30 +02:00
|
|
|
user_id_hash = bcrypt.hashpw(user_id, bcrypt.gensalt())
|
2019-10-06 23:49:00 +02:00
|
|
|
responses \
|
|
|
|
.get(str(choice)) \
|
|
|
|
.append(user_id_hash.decode())
|
2019-10-06 01:49:30 +02:00
|
|
|
else:
|
2019-10-06 23:49:00 +02:00
|
|
|
print(responses.get(str(choice)))
|
|
|
|
print(103)
|
|
|
|
for i, responder in enumerate(responses.get(str(choice))):
|
|
|
|
print(105)
|
2019-10-06 01:49:30 +02:00
|
|
|
if bcrypt.checkpw(user_id, responder.encode()):
|
2019-10-06 23:49:00 +02:00
|
|
|
print(107)
|
|
|
|
responses \
|
|
|
|
.get(str(choice)) \
|
|
|
|
.pop(i)
|
2019-10-06 01:49:30 +02:00
|
|
|
else:
|
2019-10-06 23:49:00 +02:00
|
|
|
print(112)
|
2019-10-06 01:49:30 +02:00
|
|
|
user_id_hash = bcrypt.hashpw(user_id, bcrypt.gensalt())
|
2019-10-06 23:49:00 +02:00
|
|
|
responses \
|
|
|
|
.get(str(choice)) \
|
|
|
|
.append(user_id_hash.decode())
|
|
|
|
print(117)
|
2019-10-06 01:49:30 +02:00
|
|
|
|
2019-10-06 23:49:00 +02:00
|
|
|
poll.responses = json.dumps(responses)
|
|
|
|
self.bot.database.session.commit()
|
|
|
|
await self.update_poll(poll.id)
|
2019-10-06 01:49:30 +02:00
|
|
|
|
2019-09-28 01:39:45 +02:00
|
|
|
"""---------------------------------------------------------------------"""
|
|
|
|
|
2019-10-06 01:49:30 +02:00
|
|
|
async def make_poll(self, ctx: commands.Context, poll: str, anonymous):
|
|
|
|
question = (poll.split('|')[0]).strip()
|
|
|
|
responses = [response.strip() for response in poll.split('|')[1:]]
|
|
|
|
responses_row = {}
|
|
|
|
emotes = utils_emotes.get(len(responses))
|
|
|
|
|
|
|
|
stmt = await ctx.send(Texts('poll', ctx).get('**Preparation...**'))
|
|
|
|
|
|
|
|
poll_row = Poll()
|
2019-10-06 23:49:00 +02:00
|
|
|
self.bot.database.session.add(poll_row)
|
|
|
|
self.bot.database.session.flush()
|
2019-10-06 01:49:30 +02:00
|
|
|
|
|
|
|
e = discord.Embed(description=f"**{question}**")
|
|
|
|
e.set_author(
|
|
|
|
name=ctx.author,
|
2019-10-06 23:49:00 +02:00
|
|
|
icon_url="https://cdn.gnous.eu/tuxbot/survey1.png"
|
2019-10-06 01:49:30 +02:00
|
|
|
)
|
|
|
|
for i, response in enumerate(responses):
|
2019-10-06 23:49:00 +02:00
|
|
|
responses_row[str(i + 1)] = []
|
2019-10-06 01:49:30 +02:00
|
|
|
e.add_field(
|
|
|
|
name=f"{emotes[i]} __{response.capitalize()}__",
|
|
|
|
value="**0** vote"
|
|
|
|
)
|
|
|
|
e.set_footer(text=f"ID: {poll_row.id}")
|
|
|
|
|
|
|
|
poll_row.message_id = stmt.id
|
2019-10-06 23:49:00 +02:00
|
|
|
poll_row.channel_id = stmt.channel.id
|
|
|
|
poll_row.content = e.to_dict()
|
2019-10-06 01:49:30 +02:00
|
|
|
poll_row.is_anonymous = anonymous
|
|
|
|
poll_row.responses = responses_row
|
|
|
|
|
2019-10-06 23:49:00 +02:00
|
|
|
self.bot.database.session.commit()
|
2019-10-06 01:49:30 +02:00
|
|
|
|
|
|
|
await stmt.edit(content='', embed=e)
|
|
|
|
for emote in range(len(responses)):
|
|
|
|
await stmt.add_reaction(emotes[emote])
|
|
|
|
|
2019-09-28 01:39:45 +02:00
|
|
|
@commands.group(name='sondage', aliases=['poll'])
|
2019-10-06 01:49:30 +02:00
|
|
|
async def _poll(self, ctx: commands.Context):
|
|
|
|
if ctx.invoked_subcommand is None:
|
|
|
|
...
|
|
|
|
|
|
|
|
@_poll.group(name='create', aliases=['new', 'nouveau'])
|
|
|
|
async def _poll_create(self, ctx: commands.Context, *, poll: str):
|
|
|
|
is_anonymous = '--anonyme' in poll
|
|
|
|
poll = poll.replace('--anonyme', '')
|
|
|
|
|
|
|
|
await self.make_poll(ctx, poll, anonymous=is_anonymous)
|
2019-09-28 01:39:45 +02:00
|
|
|
|
|
|
|
|
|
|
|
def setup(bot: TuxBot):
|
2019-10-06 01:49:30 +02:00
|
|
|
bot.add_cog(Polls(bot))
|