2026-01-14 21:32:20 +01:00
|
|
|
"""
|
|
|
|
|
Ticket Permissions Utility
|
|
|
|
|
==========================
|
|
|
|
|
Centralized permission logic for the ticket system.
|
|
|
|
|
"""
|
2026-05-06 17:07:09 +02:00
|
|
|
import disnake
|
2026-01-14 21:32:20 +01:00
|
|
|
from typing import TYPE_CHECKING, Optional
|
|
|
|
|
|
|
|
|
|
if TYPE_CHECKING:
|
2026-05-01 16:16:33 +02:00
|
|
|
from ..data.models import GuildTicketConfig, TicketCategory
|
2026-01-14 21:32:20 +01:00
|
|
|
|
2026-05-06 17:07:09 +02:00
|
|
|
def is_staff(interaction: disnake.Interaction, config: 'GuildTicketConfig', category: Optional['TicketCategory'] = None) -> bool:
|
2026-01-14 21:32:20 +01:00
|
|
|
"""
|
|
|
|
|
Check if the user has staff permissions.
|
|
|
|
|
|
2026-05-01 16:16:33 +02:00
|
|
|
If a category is provided and has specific staff_roles defined,
|
|
|
|
|
only those roles (and admins) are considered staff for this check.
|
|
|
|
|
Otherwise, global staff roles from the config are used.
|
2026-01-14 21:32:20 +01:00
|
|
|
"""
|
|
|
|
|
# Get user and permissions based on object type
|
|
|
|
|
user = getattr(interaction, "author", getattr(interaction, "user", None))
|
|
|
|
|
if not user:
|
|
|
|
|
return False
|
|
|
|
|
|
|
|
|
|
if user.guild_permissions.administrator:
|
|
|
|
|
return True
|
|
|
|
|
|
2026-05-01 16:16:33 +02:00
|
|
|
# Check specific users (always allowed)
|
2026-01-14 21:32:20 +01:00
|
|
|
if user.id in config.staff_users:
|
|
|
|
|
return True
|
|
|
|
|
|
2026-05-01 16:16:33 +02:00
|
|
|
# If category has specific roles, only those are allowed
|
|
|
|
|
if category and category.staff_roles:
|
|
|
|
|
for role_id in category.staff_roles:
|
|
|
|
|
try:
|
|
|
|
|
role = interaction.guild.get_role(int(role_id))
|
|
|
|
|
if role and role in user.roles:
|
|
|
|
|
return True
|
|
|
|
|
except (ValueError, TypeError):
|
|
|
|
|
continue
|
|
|
|
|
return False
|
|
|
|
|
|
|
|
|
|
# Check global roles
|
2026-01-14 21:32:20 +01:00
|
|
|
for role_id in config.staff_roles:
|
2026-05-01 16:16:33 +02:00
|
|
|
try:
|
|
|
|
|
role = interaction.guild.get_role(int(role_id))
|
|
|
|
|
if role and role in user.roles:
|
|
|
|
|
return True
|
|
|
|
|
except (ValueError, TypeError):
|
|
|
|
|
continue
|
2026-01-14 21:32:20 +01:00
|
|
|
|
|
|
|
|
return False
|
|
|
|
|
|
2026-05-06 17:07:09 +02:00
|
|
|
def can_access_config(interaction: disnake.Interaction, config: 'GuildTicketConfig') -> bool:
|
2026-01-14 21:32:20 +01:00
|
|
|
"""
|
|
|
|
|
Check if the user can access the configuration.
|
|
|
|
|
|
|
|
|
|
Checks:
|
|
|
|
|
1. Administrator permission
|
|
|
|
|
2. Config roles
|
|
|
|
|
3. Config users
|
|
|
|
|
4. Staff permissions (staff can often access basic config or view panels)
|
|
|
|
|
Note: This function is strictly for CONFIG access.
|
|
|
|
|
If staff should access config, add them to config roles or check is_staff too.
|
|
|
|
|
In this implementation, we check specific config permissions.
|
|
|
|
|
"""
|
|
|
|
|
# Get user and permissions based on object type
|
|
|
|
|
user = getattr(interaction, "author", getattr(interaction, "user", None))
|
|
|
|
|
if not user:
|
|
|
|
|
return False
|
|
|
|
|
|
|
|
|
|
if user.guild_permissions.administrator:
|
|
|
|
|
return True
|
|
|
|
|
|
|
|
|
|
# Check specific users
|
|
|
|
|
if user.id in config.config_users:
|
|
|
|
|
return True
|
|
|
|
|
|
|
|
|
|
# Check config roles
|
|
|
|
|
for role_id in config.config_roles:
|
|
|
|
|
role = interaction.guild.get_role(int(role_id))
|
|
|
|
|
if role and role in user.roles:
|
|
|
|
|
return True
|
|
|
|
|
|
|
|
|
|
# Also check legacy/migrated staff roles if they imply config access?
|
|
|
|
|
# For now, we keep it strict: config access requires explicit config permission.
|
|
|
|
|
|
|
|
|
|
return False
|
|
|
|
|
|
2026-05-06 17:07:09 +02:00
|
|
|
def is_whitelisted(interaction: disnake.Interaction, config: 'GuildTicketConfig', bot) -> bool:
|
2026-01-14 21:32:20 +01:00
|
|
|
"""
|
|
|
|
|
Check if user is whitelisted or has staff/config permissions.
|
|
|
|
|
"""
|
|
|
|
|
# Staff and config users are always whitelisted
|
|
|
|
|
if is_staff(interaction, config) or can_access_config(interaction, config):
|
|
|
|
|
return True
|
|
|
|
|
|
|
|
|
|
# Check whitelist cog
|
|
|
|
|
whitelist_cog = bot.get_cog("WhitelistMonitor")
|
|
|
|
|
if not whitelist_cog:
|
|
|
|
|
# If whitelist system not available, deny unless staff/config
|
|
|
|
|
return False
|
|
|
|
|
|
|
|
|
|
return whitelist_cog.is_whitelisted(interaction.guild.id, interaction.user.id)
|