Temporary group vcs and a bunch of fixes
This commit is contained in:
99
bot.py
99
bot.py
@@ -13,7 +13,7 @@ from dotenv import load_dotenv
|
||||
|
||||
from lib.config import config, config_meta, config_load, config_save, config_get, config_set, config_get_descriptions, \
|
||||
config_set_raw
|
||||
from lib.utils import async_filter, find_category
|
||||
from lib.utils import async_filter, find_category, find_role_case_insensitive
|
||||
|
||||
load_dotenv()
|
||||
TOKEN = os.getenv('DISCORD_TOKEN')
|
||||
@@ -49,6 +49,7 @@ OCH_LOEH_SOUND = "assets/och_loeh.mp3"
|
||||
config_load()
|
||||
intents = discord.Intents.default()
|
||||
intents.members = True
|
||||
intents.voice_states = True
|
||||
bot = commands.Bot(command_prefix=config.get('prefix'), intents=intents)
|
||||
|
||||
if 'LIBOPUS' in os.environ and not len(os.environ['LIBOPUS']) == 0:
|
||||
@@ -200,6 +201,21 @@ async def on_message(message: discord.Message):
|
||||
await bot.process_commands(message)
|
||||
|
||||
|
||||
@bot.event
|
||||
async def on_voice_state_update(member: discord.Member, before: discord.VoiceState, after: discord.VoiceState):
|
||||
if after.channel is None and before.channel is not None:
|
||||
channel: discord.VoiceChannel = before.channel
|
||||
if not channel.voice_states:
|
||||
if channel.category is not None and channel.name.endswith("_vc"):
|
||||
if channel.category.name.lower() == config_get("groups-category", channel.guild.id).lower():
|
||||
name: str = channel.name[:-3]
|
||||
role = await find_role_case_insensitive(channel.guild, name,
|
||||
config_get("groups-role-prefix", channel.guild.id))
|
||||
|
||||
if role is not None:
|
||||
await channel.delete(reason="Delete temporary group channel when last person left")
|
||||
|
||||
|
||||
@bot.command(name='random_message', brief='Select a random message from a channel')
|
||||
async def random_message_command(ctx: commands.Context, channel: Optional[discord.TextChannel] = None,
|
||||
max_cnt: Optional[int] = 100, reaction_filter: Optional[str] = None):
|
||||
@@ -354,13 +370,14 @@ async def group_command(ctx: commands.Context, subcommand: Optional[str], arg: O
|
||||
await ctx.send("Access denied!")
|
||||
return
|
||||
if subcommand is None:
|
||||
await ctx.send("Available commands: `list`, `create <group> <members>`, `archive <group>`, `delete <group>`")
|
||||
await ctx.send("Available commands: `list`, `create <group> <members>`, "
|
||||
"`archive <group>`, `unarchive <group>`, `delete <group>`, `clear_vcs`")
|
||||
return
|
||||
|
||||
guild: discord.Guild = ctx.guild
|
||||
role_prefix = config_get("groups-role-prefix", guild.id)
|
||||
|
||||
def collect_group_channels(cat: discord.CategoryChannel) -> dict[str, discord.TextChannel]:
|
||||
def collect_group_channels(cat: discord.CategoryChannel) -> dict[str, discord.abc.GuildChannel]:
|
||||
return {channel.name: channel for channel in cat.text_channels}
|
||||
|
||||
async def collect_group_roles() -> list[discord.Role]:
|
||||
@@ -369,9 +386,10 @@ async def group_command(ctx: commands.Context, subcommand: Optional[str], arg: O
|
||||
async def fail_category(type: str, expected: str):
|
||||
await ctx.send("Unable to find channel category \"" + expected + "\" for " + type + ". Change in configs.")
|
||||
|
||||
def link_channel(channel: discord.TextChannel, italic: bool = False) -> str:
|
||||
def link_channel(channel: discord.abc.GuildChannel, italic: bool = False) -> str:
|
||||
if italic:
|
||||
return '[*' + channel.name + '*](https://discord.com/channels/' + str(guild.id) + '/' + str(channel.id) + ')'
|
||||
return '[*' + channel.name + '*](https://discord.com/channels/' + str(guild.id) + '/' + str(
|
||||
channel.id) + ')'
|
||||
return '[' + channel.name + '](https://discord.com/channels/' + str(guild.id) + '/' + str(channel.id) + ')'
|
||||
|
||||
groups_cat = find_category(guild, config_get("groups-category", guild.id))
|
||||
@@ -414,8 +432,29 @@ async def group_command(ctx: commands.Context, subcommand: Optional[str], arg: O
|
||||
await fail_category("archive", config_get("groups-archive-category", guild.id))
|
||||
return
|
||||
await groups[channel_name].edit(reason="Archive group " + arg, category=archive_cat)
|
||||
if channel_name + "_vc" in groups:
|
||||
await groups[channel_name + "_vc"].delete(reason="Archive group" + arg)
|
||||
|
||||
await ctx.send("Group " + arg + " archived.")
|
||||
|
||||
else:
|
||||
await ctx.send("Can't find that group!")
|
||||
elif subcommand == 'unarchive':
|
||||
if arg is None:
|
||||
await ctx.send("Group name required!")
|
||||
return
|
||||
|
||||
channel_name = arg.lower()
|
||||
archive_cat = find_category(guild, config_get("groups-archive-category", guild.id))
|
||||
if archive_cat is None:
|
||||
await fail_category("archive", config_get("groups-archive-category", guild.id))
|
||||
return
|
||||
archived_groups = collect_group_channels(archive_cat)
|
||||
|
||||
if channel_name in archived_groups:
|
||||
await archived_groups[channel_name].edit(reason="Archive group " + arg, category=groups_cat)
|
||||
await ctx.send("Group " + arg + " unarchived.")
|
||||
|
||||
else:
|
||||
await ctx.send("Can't find that group!")
|
||||
elif subcommand == 'delete':
|
||||
@@ -428,18 +467,18 @@ async def group_command(ctx: commands.Context, subcommand: Optional[str], arg: O
|
||||
await fail_category("archive", config_get("groups-archive-category", guild.id))
|
||||
return
|
||||
|
||||
active_groups = collect_group_channels(groups_cat)
|
||||
archive_groups = collect_group_channels(archive_cat)
|
||||
|
||||
role = guild.get_role(config_get("groups-role-prefix", guild.id) + arg)
|
||||
role = await find_role_case_insensitive(guild, arg, role_prefix)
|
||||
if role is not None:
|
||||
await role.delete(reason="Delete group " + arg)
|
||||
|
||||
groups = collect_group_channels(groups_cat)
|
||||
groups.update(collect_group_channels(archive_cat))
|
||||
|
||||
channel_name = arg.lower()
|
||||
if channel_name in active_groups:
|
||||
await active_groups[channel_name].delete(reason="Delete group " + arg)
|
||||
if channel_name in archive_groups:
|
||||
await archive_groups[channel_name].delete(reason="Delete group " + arg)
|
||||
if channel_name in groups:
|
||||
await groups[channel_name].delete(reason="Delete group " + arg)
|
||||
if channel_name + "_vc" in groups:
|
||||
await groups[channel_name + "_vc"].delete(reason="Delete group " + arg)
|
||||
|
||||
await ctx.send("Group " + arg + " deleted.")
|
||||
elif subcommand == 'create':
|
||||
@@ -463,6 +502,40 @@ async def group_command(ctx: commands.Context, subcommand: Optional[str], arg: O
|
||||
await asyncio.sleep(5)
|
||||
await channel.send("Hi, " + role.mention)
|
||||
await ctx.send("Group " + arg + " created.")
|
||||
elif subcommand == 'clear_vcs':
|
||||
cors: list[coroutine] = []
|
||||
for vc in groups_cat.voice_channels:
|
||||
cors.append(vc.delete(reason="Clear temporary vcs, as requested by " + ctx.author.mention))
|
||||
for cor in cors:
|
||||
await cor
|
||||
|
||||
|
||||
@bot.command(name='groupvc', brief='Creates a temporary vc for the current group text channel')
|
||||
async def groupvc_command(ctx: commands.Context):
|
||||
if ctx.channel.category is not None:
|
||||
guild: discord.Guild = ctx.guild
|
||||
channel: discord.TextChannel = ctx.channel
|
||||
if channel.category.name.lower() == config_get("groups-category", guild.id):
|
||||
role = await find_role_case_insensitive(guild, channel.name, config_get("groups-role-prefix", guild.id))
|
||||
if role is None:
|
||||
await ctx.send("Couldn't resolve group role!")
|
||||
return
|
||||
|
||||
category: discord.CategoryChannel = channel.category
|
||||
for vc in category.voice_channels:
|
||||
if vc.name.lower() == channel.name.lower() + "_vc":
|
||||
await ctx.send("Temporary group channel already exists.")
|
||||
return
|
||||
|
||||
vc = await category.create_voice_channel(channel.name + "_vc",
|
||||
overwrites={
|
||||
role: discord.PermissionOverwrite(view_channel=True)
|
||||
},
|
||||
reason="Create temporary vc for group " + channel.name)
|
||||
await ctx.send("Created temporary vc for this group")
|
||||
return
|
||||
|
||||
await ctx.send("Not an active group channel!")
|
||||
|
||||
|
||||
def _is_message_valid_for_selection(message: discord.Message, reaction_filter: Optional[str] = None) -> bool:
|
||||
|
||||
@@ -15,3 +15,10 @@ def find_category(guild: discord.Guild, group: str) -> Optional[discord.Category
|
||||
if cat.name.lower() == group:
|
||||
return cat
|
||||
return None
|
||||
|
||||
|
||||
async def find_role_case_insensitive(guild: discord.Guild, name: str, prefix: str = '') -> Optional[discord.Role]:
|
||||
for role in await guild.fetch_roles():
|
||||
if name.strip().lower() == role.name[len(prefix):].lower():
|
||||
return role
|
||||
return None
|
||||
|
||||
Reference in New Issue
Block a user