From ab88652cdb9d3b368b6bdc44205d7682e6e54e63 Mon Sep 17 00:00:00 2001 From: imcompiling Date: Tue, 7 Nov 2023 15:35:08 -0500 Subject: [PATCH 1/7] Automatic reformat. Guessing from vscode update. --- classes/election_cycle.py | 117 ++++++++++++++++++++++++++++---------- 1 file changed, 87 insertions(+), 30 deletions(-) diff --git a/classes/election_cycle.py b/classes/election_cycle.py index 3638217..fff8fd5 100644 --- a/classes/election_cycle.py +++ b/classes/election_cycle.py @@ -12,7 +12,12 @@ from sqlalchemy.orm import Session from classes.nominate_views import NominateView from classes.voting_views import VoteView from config import DakinyConfig -from database_setup.sql_data_classes import CouncilMembers, ElectionInformation, Votes, engine +from database_setup.sql_data_classes import ( + CouncilMembers, + ElectionInformation, + Votes, + engine, +) from utils import build_votes_str, get_datetime, get_election_cycle_name @@ -40,9 +45,15 @@ class ElectionCycle: self.term_end: datetime = get_datetime(self.election_cycle.term_end) self.voting_start: datetime = get_datetime(self.election_cycle.voting_start) self.voting_end: datetime = get_datetime(self.election_cycle.voting_end) - self.highcouncil_election_announce: datetime = get_datetime(self.election_cycle.highcouncil_election_announce) - self.highcouncil_election_start: datetime = get_datetime(self.election_cycle.highcouncil_election_start) - self.highcouncil_election_end: datetime = get_datetime(self.election_cycle.highcouncil_election_end) + self.highcouncil_election_announce: datetime = get_datetime( + self.election_cycle.highcouncil_election_announce + ) + self.highcouncil_election_start: datetime = get_datetime( + self.election_cycle.highcouncil_election_start + ) + self.highcouncil_election_end: datetime = get_datetime( + self.election_cycle.highcouncil_election_end + ) self.guild: nextcord.Guild = guild self.election_over: bool = False @@ -55,11 +66,15 @@ class ElectionCycle: long. """ - with open("bot_messages/election_announcement.txt", mode="r", encoding="utf8") as file: + with open( + "bot_messages/election_announcement.txt", mode="r", encoding="utf8" + ) as file: message = file.read() next_election = get_datetime( - self.config.election_cycles[(self.cycle + 1) % len(self.config.election_cycles)].election_start + self.config.election_cycles[ + (self.cycle + 1) % len(self.config.election_cycles) + ].election_start ) message = message.format( @@ -84,14 +99,22 @@ class ElectionCycle: str: Message to send. """ - with open("bot_messages/highcouncil_election.txt", mode="r", encoding="utf8") as file: + with open( + "bot_messages/highcouncil_election.txt", mode="r", encoding="utf8" + ) as file: message = file.read() return message.format( clan_council_elect_role_id=self.config.params.clan_council_elect_role_id, - highcouncil_election_announce=self.highcouncil_election_announce.strftime("%B %d"), - highcouncil_election_start=self.highcouncil_election_start.strftime("%B %d"), - highcouncil_election_end=self.highcouncil_election_end.strftime("%B %d"), + highcouncil_election_announce=self.highcouncil_election_announce.strftime( + "%B %d" + ), + highcouncil_election_start=self.highcouncil_election_start.strftime( + "%B %d" + ), + highcouncil_election_end=self.highcouncil_election_end.strftime( + "%B %d" + ), term_start=self.term_start.strftime("%B %d"), ) @@ -103,7 +126,9 @@ class ElectionCycle: str: Message to send. """ - with open("bot_messages/highcouncil_vote.txt", mode="r", encoding="utf8") as file: + with open( + "bot_messages/highcouncil_vote.txt", mode="r", encoding="utf8" + ) as file: message = file.read() return message.format( @@ -121,7 +146,9 @@ class ElectionCycle: with open("bot_messages/vote_start.txt", mode="r", encoding="utf8") as file: message = file.read() - vote_end: datetime = get_datetime(self.config.election_cycles[self.cycle].voting_end) + vote_end: datetime = get_datetime( + self.config.election_cycles[self.cycle].voting_end + ) return message.format( clan_member_id=self.config.params.clan_member_role_id, @@ -140,7 +167,11 @@ class ElectionCycle: await self.election_start_action() elif today.date() == self.voting_start.date(): await self.voting_start_action() - elif (self.voting_end - timedelta(3)).date() <= today.date() < self.voting_end.date(): + elif ( + (self.voting_end - timedelta(3)).date() + <= today.date() + < self.voting_end.date() + ): await self.election_reminder() elif today.date() == self.voting_end.date(): await self.voting_end_action() @@ -158,9 +189,9 @@ class ElectionCycle: quarter_name: str = get_election_cycle_name(self.config) # create new entry into database. - election_channel: nextcord.TextChannel = await category.create_text_channel(quarter_name) - clan_member_role: nextcord.Role = self.guild.get_role(self.config.params.clan_member_role_id) - await election_channel.set_permissions(clan_member_role, add_reactions=True) + clan_member_role: nextcord.Role = self.guild.get_role( + self.config.params.clan_member_role_id + ) with Session(engine) as session: new_cycle = ElectionInformation(ElectionCycle=quarter_name, ElectionChannel=election_channel.id) session.add(new_cycle) @@ -183,14 +214,21 @@ class ElectionCycle: Removes write permission from the general clan member role. """ message = self.build_vote_start() - clan_member_role: nextcord.Role = self.guild.get_role(self.config.params.clan_member_role_id) - election_channel: nextcord.TextChannel = self.guild.get_channel(self.get_election_info().ElectionChannel) + clan_member_role: nextcord.Role = self.guild.get_role( + self.config.params.clan_member_role_id + ) + election_channel: nextcord.TextChannel = self.guild.get_channel( + self.get_election_info().ElectionChannel + ) await election_channel.send(message) - vote_msg = await election_channel.send(build_votes_str(self.config), view=VoteView(self.config, self.guild)) + vote_msg = await election_channel.send( + build_votes_str(self.config), view=VoteView(self.config, self.guild) + ) with Session(engine) as session: stmt = select(ElectionInformation).where( - ElectionInformation.ElectionCycle == get_election_cycle_name(self.config) + ElectionInformation.ElectionCycle + == get_election_cycle_name(self.config) ) info = session.scalar(stmt) info.CouncilVoteMsgId = vote_msg.id @@ -204,9 +242,15 @@ class ElectionCycle: """ message = self.build_highcouncil_election_announce() - council_elect_role: nextcord.Role = self.guild.get_role(self.config.params.clan_council_elect_role_id) - election_channel: nextcord.TextChannel = self.guild.get_channel(self.get_election_info().ElectionChannel) - clan_member_role: nextcord.Role = self.guild.get_role(self.config.params.clan_member_role_id) + council_elect_role: nextcord.Role = self.guild.get_role( + self.config.params.clan_council_elect_role_id + ) + election_channel: nextcord.TextChannel = self.guild.get_channel( + self.get_election_info().ElectionChannel + ) + clan_member_role: nextcord.Role = self.guild.get_role( + self.config.params.clan_member_role_id + ) # remove vote button from vote message election_name = get_election_cycle_name(self.config) @@ -239,7 +283,9 @@ class ElectionCycle: await user.add_roles(council_elect_role) await election_channel.send(message) - await election_channel.set_permissions(council_elect_role, send_messages=True, add_reactions=True) + await election_channel.set_permissions( + council_elect_role, send_messages=True, add_reactions=True + ) await election_channel.set_permissions(clan_member_role, add_reactions=False) async def highcouncil_election_start_action(self) -> None: @@ -248,7 +294,9 @@ class ElectionCycle: """ message = self.build_highcouncil_vote_start() - election_channel: nextcord.TextChannel = self.guild.get_channel(self.get_election_info().ElectionChannel) + election_channel: nextcord.TextChannel = self.guild.get_channel( + self.get_election_info().ElectionChannel + ) await election_channel.send(message) async def term_start_action(self) -> None: @@ -257,8 +305,12 @@ class ElectionCycle: """ self.election_over = True - election_channel: nextcord.TextChannel = self.guild.get_channel(self.get_election_info().ElectionChannel) - archive: nextcord.CategoryChannel = self.guild.get_channel(self.config.params.archive_channel_group_id) + election_channel: nextcord.TextChannel = self.guild.get_channel( + self.get_election_info().ElectionChannel + ) + archive: nextcord.CategoryChannel = self.guild.get_channel( + self.config.params.archive_channel_group_id + ) await election_channel.move(beginning=True, category=archive) @@ -272,7 +324,8 @@ class ElectionCycle: with Session(engine) as session: stmt = select(ElectionInformation).where( - ElectionInformation.ElectionCycle == get_election_cycle_name(self.config) + ElectionInformation.ElectionCycle + == get_election_cycle_name(self.config) ) return session.scalar(stmt) @@ -281,9 +334,13 @@ class ElectionCycle: Sends a message to general chat reminder clan about election. """ - general: nextcord.TextChannel = self.guild.get_channel(self.config.params.general_channel_id) + general: nextcord.TextChannel = self.guild.get_channel( + self.config.params.general_channel_id + ) message = f"Reminder to <@&{self.config.params.clan_member_role_id}>! Clan elections are happening! Head over " - message += f"to <#{self.get_election_info().ElectionChannel}> to cast your vote!" + message += ( + f"to <#{self.get_election_info().ElectionChannel}> to cast your vote!" + ) await general.send(content=message) From 8d2f2f7dbaff3ac0f6d7cc0383eae7680a0642ea Mon Sep 17 00:00:00 2001 From: imcompiling Date: Tue, 7 Nov 2023 15:36:33 -0500 Subject: [PATCH 2/7] Thread create ini election start. Modified config and database to use threads. --- classes/election_cycle.py | 14 ++++++++++---- config.py | 1 + database_setup/database.sql | 2 +- 3 files changed, 12 insertions(+), 5 deletions(-) diff --git a/classes/election_cycle.py b/classes/election_cycle.py index fff8fd5..9729978 100644 --- a/classes/election_cycle.py +++ b/classes/election_cycle.py @@ -185,15 +185,21 @@ class ElectionCycle: Performs required actions for when the election cycle starts. """ # create new channel for election - category: nextcord.CategoryChannel = self.guild.get_channel(self.config.params.active_category_id) + parent: nextcord.TextChannel = self.guild.get_channel( + self.config.params.voting_parent_id + ) quarter_name: str = get_election_cycle_name(self.config) # create new entry into database. + thread: nextcord.Thread = await parent.create_thread(quarter_name) clan_member_role: nextcord.Role = self.guild.get_role( self.config.params.clan_member_role_id ) + await thread.set_permissions(clan_member_role, add_reactions=True) with Session(engine) as session: - new_cycle = ElectionInformation(ElectionCycle=quarter_name, ElectionChannel=election_channel.id) + new_cycle = ElectionInformation( + ElectionCycle=quarter_name, ThreadId=thread.id + ) session.add(new_cycle) session.commit() @@ -204,9 +210,9 @@ class ElectionCycle: for index, message in enumerate(messages): # if last item, add the nominate button if index + 1 == len(messages): - await election_channel.send(message, view=NominateView(self.config)) + await thread.send(message, view=NominateView(self.config)) else: - await election_channel.send(message) + await thread.send(message) async def voting_start_action(self) -> None: """ diff --git a/config.py b/config.py index 1dfc500..f7f10b1 100644 --- a/config.py +++ b/config.py @@ -22,6 +22,7 @@ class Params: general_channel_id: int guild_id: int high_council_role_id: int + voting_parent_id: int @dataclass diff --git a/database_setup/database.sql b/database_setup/database.sql index 299e621..64f77a9 100644 --- a/database_setup/database.sql +++ b/database_setup/database.sql @@ -1,6 +1,6 @@ CREATE TABLE ElectionInformation( ElectionCycle varchar(30) not null unique, - ElectionChannel bigint unsigned not null, + ThreadId bigint unsigned not null, CouncilVoteMsgId bigint unsigned, PRIMARY KEY (ElectionCycle) ); From 75fc59ed5e1013ae48dfefd06e0f1f6933659bf5 Mon Sep 17 00:00:00 2001 From: imcompiling Date: Wed, 8 Nov 2023 15:30:05 -0500 Subject: [PATCH 3/7] Removed references to ElectionChannel. Removed permission managing as threads don't have permissions. --- classes/election_cycle.py | 48 +++++++++++---------------------------- 1 file changed, 13 insertions(+), 35 deletions(-) diff --git a/classes/election_cycle.py b/classes/election_cycle.py index 9729978..55c2ff5 100644 --- a/classes/election_cycle.py +++ b/classes/election_cycle.py @@ -220,14 +220,11 @@ class ElectionCycle: Removes write permission from the general clan member role. """ message = self.build_vote_start() - clan_member_role: nextcord.Role = self.guild.get_role( - self.config.params.clan_member_role_id + election_thread: nextcord.Thread = self.guild.get_thread( + self.get_election_info().ThreadId ) - election_channel: nextcord.TextChannel = self.guild.get_channel( - self.get_election_info().ElectionChannel - ) - await election_channel.send(message) - vote_msg = await election_channel.send( + await election_thread.send(message) + vote_msg = await election_thread.send( build_votes_str(self.config), view=VoteView(self.config, self.guild) ) @@ -240,8 +237,6 @@ class ElectionCycle: info.CouncilVoteMsgId = vote_msg.id session.commit() - await election_channel.set_permissions(clan_member_role, send_messages=False) - async def voting_end_action(self) -> None: """ Performs required actions for when voting time has ended. @@ -251,11 +246,8 @@ class ElectionCycle: council_elect_role: nextcord.Role = self.guild.get_role( self.config.params.clan_council_elect_role_id ) - election_channel: nextcord.TextChannel = self.guild.get_channel( - self.get_election_info().ElectionChannel - ) - clan_member_role: nextcord.Role = self.guild.get_role( - self.config.params.clan_member_role_id + election_thread: nextcord.Thread = self.guild.get_thread( + self.get_election_info().ThreadId ) # remove vote button from vote message @@ -265,7 +257,7 @@ class ElectionCycle: ElectionInformation.ElectionCycle == election_name ) vote_msg_id = session.scalar(stmt) - vote_msg: nextcord.Message = await election_channel.fetch_message(vote_msg_id) + vote_msg: nextcord.Message = await election_thread.fetch_message(vote_msg_id) await vote_msg.edit(view=None) # add the highcouncil role to everyone with 3 or more votes. set elected to true in database @@ -288,11 +280,7 @@ class ElectionCycle: await user.add_roles(council_elect_role) - await election_channel.send(message) - await election_channel.set_permissions( - council_elect_role, send_messages=True, add_reactions=True - ) - await election_channel.set_permissions(clan_member_role, add_reactions=False) + await election_thread.send(message) async def highcouncil_election_start_action(self) -> None: """ @@ -300,25 +288,17 @@ class ElectionCycle: """ message = self.build_highcouncil_vote_start() - election_channel: nextcord.TextChannel = self.guild.get_channel( - self.get_election_info().ElectionChannel + election_thread: nextcord.Thread = self.guild.get_thread( + self.get_election_info().ThreadId ) - await election_channel.send(message) + await election_thread.send(message) async def term_start_action(self) -> None: """ - Moves the election channel into the archive category. + Marks the election as over. """ self.election_over = True - election_channel: nextcord.TextChannel = self.guild.get_channel( - self.get_election_info().ElectionChannel - ) - archive: nextcord.CategoryChannel = self.guild.get_channel( - self.config.params.archive_channel_group_id - ) - - await election_channel.move(beginning=True, category=archive) def get_election_info(self) -> ElectionInformation: """ @@ -345,8 +325,6 @@ class ElectionCycle: ) message = f"Reminder to <@&{self.config.params.clan_member_role_id}>! Clan elections are happening! Head over " - message += ( - f"to <#{self.get_election_info().ElectionChannel}> to cast your vote!" - ) + message += f"to <#{self.get_election_info().ThreadId}> to cast your vote!" await general.send(content=message) From c38632ca21d8e9f635ef42b666ba54367750c7f7 Mon Sep 17 00:00:00 2001 From: imcompiling Date: Wed, 8 Nov 2023 15:43:58 -0500 Subject: [PATCH 4/7] Remove another permission setting. name a parameter. --- classes/election_cycle.py | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/classes/election_cycle.py b/classes/election_cycle.py index 55c2ff5..0442408 100644 --- a/classes/election_cycle.py +++ b/classes/election_cycle.py @@ -191,11 +191,7 @@ class ElectionCycle: quarter_name: str = get_election_cycle_name(self.config) # create new entry into database. - thread: nextcord.Thread = await parent.create_thread(quarter_name) - clan_member_role: nextcord.Role = self.guild.get_role( - self.config.params.clan_member_role_id - ) - await thread.set_permissions(clan_member_role, add_reactions=True) + thread: nextcord.Thread = await parent.create_thread(name=quarter_name) with Session(engine) as session: new_cycle = ElectionInformation( ElectionCycle=quarter_name, ThreadId=thread.id From c98bb5888c81f5d4732f8598decb94085673d463 Mon Sep 17 00:00:00 2001 From: imcompiling Date: Wed, 8 Nov 2023 15:44:19 -0500 Subject: [PATCH 5/7] Give a message for thread to attach to. Lets it be public. --- classes/election_cycle.py | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/classes/election_cycle.py b/classes/election_cycle.py index 0442408..7a7fafb 100644 --- a/classes/election_cycle.py +++ b/classes/election_cycle.py @@ -190,8 +190,12 @@ class ElectionCycle: ) quarter_name: str = get_election_cycle_name(self.config) + thread_msg: nextcord.Message = await parent.send(content=quarter_name) + # create new entry into database. - thread: nextcord.Thread = await parent.create_thread(name=quarter_name) + thread: nextcord.Thread = await parent.create_thread( + name=quarter_name, message=thread_msg + ) with Session(engine) as session: new_cycle = ElectionInformation( ElectionCycle=quarter_name, ThreadId=thread.id From 27f90bbaef3ee76324f0f19e8c146642bbfb9cb0 Mon Sep 17 00:00:00 2001 From: imcompiling Date: Wed, 8 Nov 2023 15:51:06 -0500 Subject: [PATCH 6/7] Add test for term start. --- cogs/commands/test.py | 40 +++++++++++++++++++++++++++++++++++----- 1 file changed, 35 insertions(+), 5 deletions(-) diff --git a/cogs/commands/test.py b/cogs/commands/test.py index 1838b08..2ee737d 100644 --- a/cogs/commands/test.py +++ b/cogs/commands/test.py @@ -61,7 +61,11 @@ class TestCog(commands.Cog, name="Test commands."): """ config: DakinyConfig = self.bot.config - cycle = ElectionCycle(get_current_cycle(config), config, self.bot.get_guild(config.params.guild_id)) + cycle = ElectionCycle( + get_current_cycle(config), + config, + self.bot.get_guild(config.params.guild_id), + ) await cycle.election_start_action() @test.subcommand() @@ -73,7 +77,11 @@ class TestCog(commands.Cog, name="Test commands."): interaction (nextcord.Interaction): _description_ """ config: DakinyConfig = self.bot.config - cycle = ElectionCycle(get_current_cycle(config), config, self.bot.get_guild(config.params.guild_id)) + cycle = ElectionCycle( + get_current_cycle(config), + config, + self.bot.get_guild(config.params.guild_id), + ) await cycle.voting_start_action() @test.subcommand() @@ -85,17 +93,39 @@ class TestCog(commands.Cog, name="Test commands."): interaction (nextcord.Interaction): _description_ """ config: DakinyConfig = self.bot.config - cycle = ElectionCycle(get_current_cycle(config), config, self.bot.get_guild(config.params.guild_id)) + cycle = ElectionCycle( + get_current_cycle(config), + config, + self.bot.get_guild(config.params.guild_id), + ) await cycle.voting_end_action() @test.subcommand() async def election_reminder(self, interaction: nextcord.Interaction): config: DakinyConfig = self.bot.config - cycle = ElectionCycle(get_current_cycle(config), config, self.bot.get_guild(config.params.guild_id)) + cycle = ElectionCycle( + get_current_cycle(config), + config, + self.bot.get_guild(config.params.guild_id), + ) await cycle.election_reminder() @test.subcommand() async def daily(self, interaction: nextcord.Interaction): config: DakinyConfig = self.bot.config - cycle = ElectionCycle(get_current_cycle(config), config, self.bot.get_guild(config.params.guild_id)) + cycle = ElectionCycle( + get_current_cycle(config), + config, + self.bot.get_guild(config.params.guild_id), + ) await cycle.check_date() + + @test.subcommand() + async def term_start(self, interaction: nextcord.Interaction): + config: DakinyConfig = self.bot.config + cycle = ElectionCycle( + get_current_cycle(config), + config, + self.bot.get_guild(config.params.guild_id), + ) + await cycle.term_start_action() From 431e9c0b353f921ce916b275d5f711c39c64228f Mon Sep 17 00:00:00 2001 From: imcompiling Date: Wed, 8 Nov 2023 16:11:47 -0500 Subject: [PATCH 7/7] Filled out term start action. --- classes/election_cycle.py | 10 ++++++++++ cogs/commands/test.py | 7 +++++++ 2 files changed, 17 insertions(+) diff --git a/classes/election_cycle.py b/classes/election_cycle.py index 7a7fafb..3197891 100644 --- a/classes/election_cycle.py +++ b/classes/election_cycle.py @@ -300,6 +300,16 @@ class ElectionCycle: self.election_over = True + election_thread: nextcord.Thread = self.guild.get_thread( + self.get_election_info().ThreadId + ) + + await election_thread.send( + "This election cycle is now over. Thank you everyone for participating!" + ) + + await election_thread.edit(archived=True, locked=True) + def get_election_info(self) -> ElectionInformation: """ Gets information for current election. diff --git a/cogs/commands/test.py b/cogs/commands/test.py index 2ee737d..8d91434 100644 --- a/cogs/commands/test.py +++ b/cogs/commands/test.py @@ -35,6 +35,7 @@ class TestCog(commands.Cog, name="Test commands."): """ @test.subcommand() + @is_me() async def msg_builder(self, interaction: nextcord.Interaction): """ Tests the message builder. @@ -52,6 +53,7 @@ class TestCog(commands.Cog, name="Test commands."): await interaction.channel.send(content=m) @test.subcommand() + @is_me() async def election_start(self, interaction: nextcord.Interaction): """ idc @@ -69,6 +71,7 @@ class TestCog(commands.Cog, name="Test commands."): await cycle.election_start_action() @test.subcommand() + @is_me() async def voting_start(self, interaction: nextcord.Interaction): """ tests the voting start action @@ -85,6 +88,7 @@ class TestCog(commands.Cog, name="Test commands."): await cycle.voting_start_action() @test.subcommand() + @is_me() async def voting_end(self, interaction: nextcord.Interaction): """ tests the voting start action @@ -101,6 +105,7 @@ class TestCog(commands.Cog, name="Test commands."): await cycle.voting_end_action() @test.subcommand() + @is_me() async def election_reminder(self, interaction: nextcord.Interaction): config: DakinyConfig = self.bot.config cycle = ElectionCycle( @@ -111,6 +116,7 @@ class TestCog(commands.Cog, name="Test commands."): await cycle.election_reminder() @test.subcommand() + @is_me() async def daily(self, interaction: nextcord.Interaction): config: DakinyConfig = self.bot.config cycle = ElectionCycle( @@ -121,6 +127,7 @@ class TestCog(commands.Cog, name="Test commands."): await cycle.check_date() @test.subcommand() + @is_me() async def term_start(self, interaction: nextcord.Interaction): config: DakinyConfig = self.bot.config cycle = ElectionCycle(