134 lines
4.2 KiB
Python
134 lines
4.2 KiB
Python
from typing import Union
|
|
|
|
from discord import Role, TextChannel, User, VoiceChannel
|
|
from discord.ext import commands
|
|
from discord_slash import SlashContext, cog_ext
|
|
from discord_slash.utils.manage_commands import create_option
|
|
|
|
from jarvis.db.types import Lock
|
|
from jarvis.utils.cachecog import CacheCog
|
|
from jarvis.utils.permissions import admin_or_permissions
|
|
|
|
|
|
class LockCog(CacheCog):
|
|
def __init__(self, bot: commands.Bot):
|
|
super().__init__(bot)
|
|
|
|
async def _lock_channel(
|
|
self,
|
|
channel: Union[TextChannel, VoiceChannel],
|
|
role: Role,
|
|
admin: User,
|
|
reason: str,
|
|
allow_send=False,
|
|
):
|
|
overrides = channel.overwrites_for(role)
|
|
if isinstance(channel, TextChannel):
|
|
overrides.send_messages = allow_send
|
|
elif isinstance(channel, VoiceChannel):
|
|
overrides.speak = allow_send
|
|
await channel.set_permissions(role, overwrite=overrides, reason=reason)
|
|
|
|
async def _unlock_channel(
|
|
self,
|
|
channel: Union[TextChannel, VoiceChannel],
|
|
role: Role,
|
|
admin: User,
|
|
):
|
|
overrides = channel.overwrites_for(role)
|
|
if isinstance(channel, TextChannel):
|
|
overrides.send_messages = None
|
|
elif isinstance(channel, VoiceChannel):
|
|
overrides.speak = None
|
|
await channel.set_permissions(role, overwrite=overrides)
|
|
|
|
@cog_ext.cog_slash(
|
|
name="lock",
|
|
description="Locks a channel",
|
|
options=[
|
|
create_option(
|
|
name="reason",
|
|
description="Lock Reason",
|
|
option_type=3,
|
|
required=True,
|
|
),
|
|
create_option(
|
|
name="duration",
|
|
description="Lock duration in minutes (default 10)",
|
|
option_type=4,
|
|
required=False,
|
|
),
|
|
create_option(
|
|
name="channel",
|
|
description="Channel to lock",
|
|
option_type=7,
|
|
required=False,
|
|
),
|
|
],
|
|
)
|
|
@admin_or_permissions(manage_channels=True)
|
|
async def _lock(
|
|
self,
|
|
ctx: SlashContext,
|
|
reason: str,
|
|
duration: int = 10,
|
|
channel: Union[TextChannel, VoiceChannel] = None,
|
|
):
|
|
await ctx.defer(hidden=True)
|
|
if duration <= 0:
|
|
await ctx.send("Duration must be > 0", hidden=True)
|
|
return
|
|
elif duration >= 300:
|
|
await ctx.send("Duration must be < 5 hours", hidden=True)
|
|
return
|
|
if len(reason) > 100:
|
|
await ctx.send("Reason must be < 100 characters", hidden=True)
|
|
return
|
|
if not channel:
|
|
channel = ctx.channel
|
|
for role in ctx.guild.roles:
|
|
try:
|
|
await self._lock_channel(channel, role, ctx.author, reason)
|
|
except Exception:
|
|
continue # Just continue on error
|
|
_ = Lock(
|
|
channel=channel.id,
|
|
guild=ctx.guild.id,
|
|
admin=ctx.author.id,
|
|
reason=reason,
|
|
duration=duration,
|
|
).insert()
|
|
await ctx.send(f"{channel.mention} locked for {duration} minute(s)")
|
|
|
|
@cog_ext.cog_slash(
|
|
name="unlock",
|
|
description="Unlocks a channel",
|
|
options=[
|
|
create_option(
|
|
name="channel",
|
|
description="Channel to lock",
|
|
option_type=7,
|
|
required=False,
|
|
),
|
|
],
|
|
)
|
|
@admin_or_permissions(manage_channels=True)
|
|
async def _unlock(
|
|
self,
|
|
ctx: SlashContext,
|
|
channel: Union[TextChannel, VoiceChannel] = None,
|
|
):
|
|
if not channel:
|
|
channel = ctx.channel
|
|
lock = Lock.get(guild=ctx.guild.id, channel=channel.id, active=True)
|
|
if not lock:
|
|
await ctx.send(f"{channel.mention} not locked.", hidden=True)
|
|
return
|
|
for role in ctx.guild.roles:
|
|
try:
|
|
await self._unlock_channel(channel, role, ctx.author)
|
|
except Exception:
|
|
continue # Just continue on error
|
|
lock.active = False
|
|
lock.update()
|
|
await ctx.send(f"{channel.mention} unlocked")
|