Compare commits

..

No commits in common. "36887f1bdfe671159d42a9d071e673abbe78280e" and "94732b7227a30bc2a4b1f6d366fd950b7b1302ac" have entirely different histories.

51 changed files with 279 additions and 230 deletions

View File

@ -14,6 +14,7 @@
"config": "src/modules/config/config.json",
"database": "src/modules/database/database.json",
"level": "src/modules/level/level.json",
"permission": "src/modules/permission/permission.json",
"technician": "src/modules/technician/technician.json",
"short-role-name": "src/modules/short_role_name/short-role-name.json",
"special-offers": "src/modules/special_offers/special-offers.json",

View File

@ -70,6 +70,7 @@
"../modules/config/config.json",
"../modules/database/database.json",
"../modules/level/level.json",
"../modules/permission/permission.json",
"../modules/short_role_name/short-role-name.json",
"../modules/special_offers/special-offers.json",
"../modules/technician/technician.json"

View File

@ -12,6 +12,7 @@ from modules.boot_log.boot_log_module import BootLogModule
from modules.config.config_module import ConfigModule
from modules.database.database_module import DatabaseModule
from modules.level.level_module import LevelModule
from modules.permission.permission_module import PermissionModule
from modules.short_role_name.short_role_name_module import ShortRoleNameModule
from modules.special_offers.special_offers_module import SteamSpecialOffersModule
from modules.technician.technician_module import TechnicianModule
@ -29,6 +30,7 @@ class ModuleList:
ConfigModule, # has to be before db check
DatabaseModule,
GraphQLModule,
PermissionModule,
AutoRoleModule,
BaseModule,
LevelModule,

View File

@ -10,7 +10,7 @@ from bot_api.model.user_dto import UserDTO
from bot_data.model.auth_role_enum import AuthRoleEnum
from bot_data.model.auth_user import AuthUser
from bot_data.model.user import User
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class AuthUserTransformer(TransformerABC):

View File

@ -15,6 +15,7 @@ class FeatureFlagsEnum(Enum):
database_module = "DatabaseModule"
level_module = "LevelModule"
moderator_module = "ModeratorModule"
permission_module = "PermissionModule"
short_role_name_module = "ShortRoleNameModule"
steam_special_offers_module = "SteamSpecialOffersModule"
# features

View File

@ -16,6 +16,7 @@ class FeatureFlagsSettings(ConfigurationModelABC):
FeatureFlagsEnum.data_module.value: True, # 03.10.2022 #56
FeatureFlagsEnum.database_module.value: True, # 02.10.2022 #48
FeatureFlagsEnum.moderator_module.value: False, # 02.10.2022 #48
FeatureFlagsEnum.permission_module.value: True, # 02.10.2022 #48
FeatureFlagsEnum.config_module.value: True, # 19.07.2023 #127
FeatureFlagsEnum.short_role_name_module.value: True, # 28.09.2023 #378
FeatureFlagsEnum.steam_special_offers_module.value: True, # 11.10.2023 #188

View File

@ -9,7 +9,7 @@ from bot_core.configuration.feature_flags_enum import FeatureFlagsEnum
from bot_core.configuration.feature_flags_settings import FeatureFlagsSettings
from bot_core.helper.command_checks import CommandChecks
from bot_core.helper.event_checks import EventChecks
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class CoreExtension(ApplicationExtensionABC):

View File

@ -7,7 +7,6 @@ from cpl_discord.service.discord_collection_abc import DiscordCollectionABC
from bot_core.abc.client_utils_abc import ClientUtilsABC
from bot_core.abc.message_service_abc import MessageServiceABC
from bot_core.abc.module_abc import ModuleABC
from bot_core.abc.permission_service_abc import PermissionServiceABC
from bot_core.configuration.feature_flags_enum import FeatureFlagsEnum
from bot_core.events.core_on_ready_event import CoreOnReadyEvent
from bot_core.pipes.date_time_offset_pipe import DateTimeOffsetPipe
@ -15,7 +14,6 @@ from bot_core.service.client_utils_service import ClientUtilsService
from bot_core.service.config_service import ConfigService
from bot_core.service.data_integrity_service import DataIntegrityService
from bot_core.service.message_service import MessageService
from bot_core.service.permission_service import PermissionService
class CoreModule(ModuleABC):
@ -30,7 +28,6 @@ class CoreModule(ModuleABC):
services.add_transient(MessageServiceABC, MessageService)
services.add_transient(ClientUtilsABC, ClientUtilsService)
services.add_transient(DataIntegrityService)
services.add_singleton(PermissionServiceABC, PermissionService)
# pipes
services.add_transient(DateTimeOffsetPipe)

View File

@ -7,7 +7,7 @@ from discord.ext.commands import Context
from bot_core.abc.client_utils_abc import ClientUtilsABC
from bot_core.abc.message_service_abc import MessageServiceABC
from bot_core.exception.check_error import CheckError
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class CommandChecks:

View File

@ -1,114 +0,0 @@
from typing import Optional
import discord
from cpl_core.configuration import ConfigurationABC
from cpl_core.logging import LoggerABC
from cpl_discord.service import DiscordBotServiceABC
from bot_data.abc.server_config_repository_abc import ServerConfigRepositoryABC
from bot_data.abc.server_repository_abc import ServerRepositoryABC
from bot_data.abc.technician_config_repository_abc import TechnicianConfigRepositoryABC
from bot_data.model.team_member_type_enum import TeamMemberTypeEnum
from bot_core.abc.permission_service_abc import PermissionServiceABC
class PermissionService(PermissionServiceABC):
def __init__(
self,
logger: LoggerABC,
bot: DiscordBotServiceABC,
config: ConfigurationABC,
servers: ServerRepositoryABC,
server_configs: ServerConfigRepositoryABC,
technician_configs: TechnicianConfigRepositoryABC,
):
PermissionServiceABC.__init__(self)
self._logger = logger
self._bot = bot
self._config = config
self._servers = servers
self._server_configs = server_configs
self._technician_configs = technician_configs
# member_id: {team_member_type: {guild_id: bool}}
self._cache: dict[int, dict[TeamMemberTypeEnum, dict[int, bool]]] = {}
def reset_cache(self):
self._cache = {}
def get_cached_permission(
self, member_id: int, team_member_type: TeamMemberTypeEnum, guild_id: int = None
) -> Optional[bool]:
if member_id not in self._cache:
self._cache[member_id] = {}
if team_member_type not in self._cache[member_id]:
self._cache[member_id][team_member_type] = {}
return None
if guild_id not in self._cache[member_id][team_member_type]:
return None
return self._cache[member_id][team_member_type][guild_id]
def set_cached_permission(
self, value: bool, member_id: int, team_member_type: TeamMemberTypeEnum, guild_id: int = None
):
if member_id not in self._cache:
self._cache[member_id] = {}
if team_member_type not in self._cache[member_id]:
self._cache[member_id][team_member_type] = {}
self._cache[member_id][team_member_type][guild_id] = value
def _has_member_role(self, member: discord.Member, team_member_type: TeamMemberTypeEnum) -> bool:
if member is None or member.guild is None:
return False
try:
has_permission_cached = self.get_cached_permission(member.id, team_member_type, member.guild.id)
if has_permission_cached is not None:
return has_permission_cached
self._logger.debug(__name__, f"Checking is member {member.name} {team_member_type.value}")
has_permission = True in [
member.guild.get_role(x.role_id) not in member.roles
for x in self._server_configs.get_server_config_by_server(
self._servers.get_server_by_discord_id(member.guild.id).id
).team_role_ids
if x.team_member_type == team_member_type
]
self.set_cached_permission(has_permission, member.id, team_member_type, member.guild.id)
return has_permission
except Exception as e:
self._logger.error(__name__, "Permission check failed", e)
return False
def is_member_admin(self, member: discord.Member) -> bool:
return self._has_member_role(member, TeamMemberTypeEnum.admin)
def is_member_moderator(self, member: discord.Member) -> bool:
return self._has_member_role(member, TeamMemberTypeEnum.moderator) or self._has_member_role(
member, TeamMemberTypeEnum.admin
)
def is_member_technician(self, member: discord.Member) -> bool:
if member is None or member.guild is None:
return False
has_permission_cached = self.get_cached_permission(member.id, TeamMemberTypeEnum.technician)
if has_permission_cached is not None:
return has_permission_cached
self._logger.debug(__name__, f"Checking is member {member.name} technician")
try:
has_permission = member.id in self._technician_configs.get_technician_config().technician_ids
self.set_cached_permission(has_permission, member.id, TeamMemberTypeEnum.technician)
return has_permission
except Exception as e:
self._logger.error(__name__, "Permission check failed", e)
return False

View File

@ -4,4 +4,3 @@ from enum import Enum
class TeamMemberTypeEnum(Enum):
moderator = "Moderator"
admin = "Admin"
technician = "Technician"

View File

@ -12,7 +12,6 @@ from bot_api.exception.service_exception import ServiceException
from bot_api.route.route import Route
from bot_core.configuration.feature_flags_enum import FeatureFlagsEnum
from bot_core.environment_variables import MAINTENANCE
from bot_core.service.permission_service import PermissionService
from bot_data.model.achievement import Achievement
from bot_data.model.auth_role_enum import AuthRoleEnum
from bot_data.model.auth_user import AuthUser
@ -33,6 +32,7 @@ from bot_data.model.user_role_enum import UserRoleEnum
from bot_graphql.abc.filter_abc import FilterABC
from bot_graphql.filter.page import Page
from bot_graphql.filter.sort import Sort
from modules.permission.service.permission_service import PermissionService
class QueryABC(ObjectType):

View File

@ -52,5 +52,4 @@ type Query {
discord: Discord
hasFeatureFlag(flag: String): FeatureFlag
featureFlags: [FeatureFlag]
}

View File

@ -40,7 +40,6 @@ type Server implements TableWithHistoryQuery {
config: ServerConfig
hasFeatureFlag(flag: String): FeatureFlag
featureFlags: [FeatureFlag]
statistic(date: String): ServerStatistic

View File

@ -6,7 +6,7 @@ from bot_data.abc.server_repository_abc import ServerRepositoryABC
from bot_data.model.achievement import Achievement
from bot_data.model.user_role_enum import UserRoleEnum
from bot_graphql.abc.query_abc import QueryABC
from bot_core.service.permission_service import PermissionService
from modules.permission.service.permission_service import PermissionService
class AchievementMutation(QueryABC):

View File

@ -10,7 +10,7 @@ from bot_data.model.scheduled_event import ScheduledEvent
from bot_data.model.scheduled_event_interval_enum import ScheduledEventIntervalEnum
from bot_data.model.user_role_enum import UserRoleEnum
from bot_graphql.abc.query_abc import QueryABC
from bot_core.service.permission_service import PermissionService
from modules.permission.service.permission_service import PermissionService
class ScheduledEventMutation(QueryABC):

View File

@ -13,7 +13,6 @@ from bot_data.model.server_team_role_ids_config import ServerTeamRoleIdsConfig
from bot_data.model.team_member_type_enum import TeamMemberTypeEnum
from bot_data.model.user_role_enum import UserRoleEnum
from bot_graphql.abc.query_abc import QueryABC
from bot_core.service.permission_service import PermissionService
class ServerConfigMutation(QueryABC):
@ -25,7 +24,6 @@ class ServerConfigMutation(QueryABC):
server_configs: ServerConfigRepositoryABC,
db: DatabaseContextABC,
config_service: ConfigService,
permissions: PermissionService,
):
QueryABC.__init__(self, "ServerConfigMutation")
@ -35,7 +33,6 @@ class ServerConfigMutation(QueryABC):
self._server_configs = server_configs
self._db = db
self._config_service = config_service
self._permissions = permissions
self.set_field("updateServerConfig", self.resolve_update_server_config)
@ -178,13 +175,11 @@ class ServerConfigMutation(QueryABC):
def _update_team_role_ids(self, new_config: ServerConfig):
old_config = self._server_configs.get_server_config_by_server(new_config.server.id)
has_update = False
for role_id in old_config.team_role_ids:
if role_id.role_id in new_config.team_role_ids.select(lambda x: int(x.role_id)):
continue
self._server_configs.delete_server_team_role_id_config(role_id)
has_update = True
for role_id in new_config.team_role_ids:
guild = self._bot.get_guild(new_config.server.discord_id)
@ -197,7 +192,3 @@ class ServerConfigMutation(QueryABC):
continue
self._server_configs.add_server_team_role_id_config(role_id)
has_update = True
if has_update:
self._permissions.reset_cache()

View File

@ -6,7 +6,7 @@ from bot_data.abc.short_role_name_repository_abc import ShortRoleNameRepositoryA
from bot_data.model.short_role_name import ShortRoleName
from bot_data.model.user_role_enum import UserRoleEnum
from bot_graphql.abc.query_abc import QueryABC
from bot_core.service.permission_service import PermissionService
from modules.permission.service.permission_service import PermissionService
class ShortRoleNameMutation(QueryABC):

View File

@ -16,7 +16,6 @@ from bot_data.model.technician_ping_url_config import TechnicianPingUrlConfig
from bot_data.model.user_role_enum import UserRoleEnum
from bot_data.service.technician_config_seeder import TechnicianConfigSeeder
from bot_graphql.abc.query_abc import QueryABC
from bot_core.service.permission_service import PermissionService
class TechnicianConfigMutation(QueryABC):
@ -31,7 +30,6 @@ class TechnicianConfigMutation(QueryABC):
config_service: ConfigService,
tech_seeder: TechnicianConfigSeeder,
client_utils: ClientUtilsABC,
permissions: PermissionService,
):
QueryABC.__init__(self, "TechnicianConfigMutation")
@ -44,7 +42,6 @@ class TechnicianConfigMutation(QueryABC):
self._config_service = config_service
self._tech_seeder = tech_seeder
self._client_utils = client_utils
self._permissions = permissions
self.set_field("updateTechnicianConfig", self.resolve_update_technician_config)
@ -129,13 +126,11 @@ class TechnicianConfigMutation(QueryABC):
def _update_technician_ids(self, new_config: TechnicianConfig):
old_config = self._technician_configs.get_technician_config()
has_update = False
for technician_id in old_config.technician_ids:
if technician_id in new_config.technician_ids:
continue
self._technician_configs.delete_technician_id_config(TechnicianIdConfig(technician_id))
has_update = True
for technician_id in new_config.technician_ids:
user = self._bot.get_user(technician_id)
@ -147,7 +142,3 @@ class TechnicianConfigMutation(QueryABC):
continue
self._technician_configs.add_technician_id_config(TechnicianIdConfig(technician_id))
has_update = True
if has_update:
self._permissions.reset_cache()

View File

@ -24,7 +24,7 @@ from bot_data.model.server_config import ServerConfig
from bot_data.model.user_joined_game_server import UserJoinedGameServer
from bot_data.model.user_role_enum import UserRoleEnum
from bot_graphql.abc.query_abc import QueryABC
from bot_core.service.permission_service import PermissionService
from modules.permission.service.permission_service import PermissionService
class UserJoinedGameServerMutation(QueryABC):

View File

@ -13,7 +13,7 @@ from bot_data.model.user_role_enum import UserRoleEnum
from bot_graphql.abc.query_abc import QueryABC
from modules.base.service.user_warnings_service import UserWarningsService
from modules.level.service.level_service import LevelService
from bot_core.service.permission_service import PermissionService
from modules.permission.service.permission_service import PermissionService
class UserMutation(QueryABC):

View File

@ -116,10 +116,6 @@ class ServerQuery(DataQueryWithHistoryABC):
"hasFeatureFlag",
lambda server, *_, **kwargs: self._resolve_has_feature_flag(server, *_, **kwargs),
)
self.set_field(
"featureFlags",
lambda server, *_, **kwargs: self._resolve_feature_flags(server, *_),
)
self.set_field("statistic", lambda server, *_, **kwargs: ServerStatistics(server, kwargs))
@staticmethod
@ -146,13 +142,3 @@ class ServerQuery(DataQueryWithHistoryABC):
"key": kwargs["flag"],
"value": FeatureFlagsSettings.get_flag_from_dict(settings.feature_flags, FeatureFlagsEnum(kwargs["flag"])),
}
def _resolve_feature_flags(self, server: Server, *_) -> list[dict]:
settings: ServerConfig = self._config.get_configuration(f"ServerConfig_{server.discord_id}")
return [
{
"key": flag,
"value": FeatureFlagsSettings.get_flag_from_dict(settings.feature_flags, FeatureFlagsEnum(flag)),
}
for flag in [e.value for e in FeatureFlagsEnum]
]

View File

@ -22,7 +22,7 @@ from bot_graphql.filter.user_joined_voice_channel_filter import (
)
from bot_graphql.filter.user_warning_filter import UserWarningFilter
from modules.level.service.level_service import LevelService
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class UserQuery(DataQueryWithHistoryABC):

View File

@ -131,10 +131,6 @@ class Query(QueryABC):
"hasFeatureFlag",
lambda *_, **kwargs: self._resolve_has_feature_flag(*_, **kwargs),
)
self.set_field(
"featureFlags",
lambda *_, **kwargs: self._resolve_feature_flags(*_),
)
def _resolve_has_feature_flag(self, *_, **kwargs):
settings: TechnicianConfig = self._config.get_configuration(TechnicianConfig)
@ -144,13 +140,3 @@ class Query(QueryABC):
"key": kwargs["flag"],
"value": FeatureFlagsSettings.get_flag_from_dict(settings.feature_flags, FeatureFlagsEnum(kwargs["flag"])),
}
def _resolve_feature_flags(self, *_) -> list[dict]:
settings: TechnicianConfig = self._config.get_configuration(TechnicianConfig)
return [
{
"key": flag,
"value": FeatureFlagsSettings.get_flag_from_dict(settings.feature_flags, FeatureFlagsEnum(flag)),
}
for flag in [e.value for e in FeatureFlagsEnum]
]

View File

@ -22,7 +22,7 @@ from bot_data.abc.server_repository_abc import ServerRepositoryABC
from bot_data.model.auto_role import AutoRole
from bot_data.model.auto_role_rule import AutoRoleRule
from bot_data.model.server_config import ServerConfig
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class AutoRoleGroup(DiscordCommandABC):

View File

@ -23,7 +23,7 @@ from bot_data.abc.user_game_ident_repository_abc import UserGameIdentRepositoryA
from bot_data.abc.user_repository_abc import UserRepositoryABC
from bot_data.model.game_server import GameServer
from bot_data.model.server_config import ServerConfig
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class GameServerGroup(DiscordCommandABC):

View File

@ -11,7 +11,7 @@ from bot_core.helper.command_checks import CommandChecks
from bot_core.logging.command_logger import CommandLogger
from bot_data.abc.server_repository_abc import ServerRepositoryABC
from bot_data.model.technician_config import TechnicianConfig
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class PingCommand(DiscordCommandABC):

View File

@ -11,7 +11,7 @@ from bot_core.abc.message_service_abc import MessageServiceABC
from bot_core.helper.command_checks import CommandChecks
from bot_core.logging.command_logger import CommandLogger
from bot_data.model.server_config import ServerConfig
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class PurgeCommand(DiscordCommandABC):

View File

@ -27,7 +27,7 @@ from bot_data.abc.user_warnings_repository_abc import UserWarningsRepositoryABC
from bot_data.model.server_config import ServerConfig
from modules.base.service.user_warnings_service import UserWarningsService
from modules.level.service.level_service import LevelService
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class UserGroup(DiscordCommandABC):

View File

@ -20,7 +20,7 @@ from bot_data.model.known_user import KnownUser
from bot_data.model.server_config import ServerConfig
from bot_data.model.user import User
from bot_data.model.user_joined_server import UserJoinedServer
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class BaseOnMemberJoinEvent(OnMemberJoinABC):

View File

@ -8,7 +8,7 @@ from bot_core.abc.message_service_abc import MessageServiceABC
from bot_core.helper.event_checks import EventChecks
from bot_data.abc.server_repository_abc import ServerRepositoryABC
from bot_data.model.server_config import ServerConfig
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class BaseOnVoiceStateUpdateEventHelpChannel(OnVoiceStateUpdateABC):

View File

@ -14,7 +14,7 @@ from bot_data.model.server_config import ServerConfig
from bot_data.model.user import User
from bot_data.model.user_warnings import UserWarnings
from modules.level.service.level_service import LevelService
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class UserWarningsService:

View File

@ -24,7 +24,7 @@ from bot_data.model.level import Level
from bot_data.model.server_config import ServerConfig
from modules.level.level_seeder import LevelSeeder
from modules.level.service.level_service import LevelService
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class LevelGroup(DiscordCommandABC):

View File

@ -6,8 +6,6 @@ from cpl_discord.container import Guild, Role, Member
from cpl_discord.service import DiscordBotServiceABC
from cpl_translation import TranslatePipe
from bot_core.configuration.feature_flags_enum import FeatureFlagsEnum
from bot_core.configuration.feature_flags_settings import FeatureFlagsSettings
from bot_core.service.message_service import MessageService
from bot_data.model.level import Level
from bot_data.model.server_config import ServerConfig
@ -40,14 +38,7 @@ class LevelService:
self._message_service = message_service
self._t = t
def _check_for_feature(self, user: User):
server_config: ServerConfig = self._config.get_configuration(f"ServerConfig_{user.server.discord_id}")
if not FeatureFlagsSettings.get_flag_from_dict(server_config.feature_flags, FeatureFlagsEnum.level_module):
raise Exception(f"Feature {FeatureFlagsEnum.level_module.value} disabled")
def get_level(self, user: User) -> Level:
self._check_for_feature(user)
levels_by_server = self._levels.get_levels_by_server_id(user.server.id)
if user.xp < 0:
return levels_by_server.order_by(lambda l: l.min_xp).first()
@ -60,7 +51,6 @@ class LevelService:
return levels.last()
async def set_level(self, user: User):
self._check_for_feature(user)
level_names = self._levels.get_levels_by_server_id(user.server.id).select(lambda l: l.name)
guild: Guild = self._bot.guilds.where(lambda g: g.id == user.server.discord_id).single()
member: Member = guild.members.where(lambda m: m.id == user.discord_id).single()

View File

@ -0,0 +1,26 @@
# -*- coding: utf-8 -*-
"""
bot sh-edraft.de Discord bot
~~~~~~~~~~~~~~~~~~~
Discord bot for customers of sh-edraft.de
:copyright: (c) 2022 - 2023 sh-edraft.de
:license: MIT, see LICENSE for more details.
"""
__title__ = "modules.permission"
__author__ = "Sven Heidemann"
__license__ = "MIT"
__copyright__ = "Copyright (c) 2022 - 2023 sh-edraft.de"
__version__ = "1.2.2"
from collections import namedtuple
# imports:
VersionInfo = namedtuple("VersionInfo", "major minor micro")
version_info = VersionInfo(major="1", minor="2", micro="2")

View File

@ -0,0 +1,26 @@
# -*- coding: utf-8 -*-
"""
bot sh-edraft.de Discord bot
~~~~~~~~~~~~~~~~~~~
Discord bot for customers of sh-edraft.de
:copyright: (c) 2022 - 2023 sh-edraft.de
:license: MIT, see LICENSE for more details.
"""
__title__ = "modules.permission.abc"
__author__ = "Sven Heidemann"
__license__ = "MIT"
__copyright__ = "Copyright (c) 2022 - 2023 sh-edraft.de"
__version__ = "1.2.2"
from collections import namedtuple
# imports
VersionInfo = namedtuple("VersionInfo", "major minor micro")
version_info = VersionInfo(major="1", minor="2", micro="2")

View File

@ -0,0 +1,44 @@
{
"ProjectSettings": {
"Name": "permission",
"Version": {
"Major": "1",
"Minor": "2",
"Micro": "2"
},
"Author": "",
"AuthorEmail": "",
"Description": "",
"LongDescription": "",
"URL": "",
"CopyrightDate": "",
"CopyrightName": "",
"LicenseName": "",
"LicenseDescription": "",
"Dependencies": [
"cpl-core==2022.12.0"
],
"DevDependencies": [
"cpl-cli==2022.12.0"
],
"PythonVersion": ">=3.10.4",
"PythonPath": {},
"Classifiers": []
},
"BuildSettings": {
"ProjectType": "library",
"SourcePath": "",
"OutputPath": "../../dist",
"Main": "permission.main",
"EntryPoint": "permission",
"IncludePackageData": false,
"Included": [],
"Excluded": [
"*/__pycache__",
"*/logs",
"*/tests"
],
"PackageData": {},
"ProjectReferences": []
}
}

View File

@ -0,0 +1,22 @@
from cpl_core.configuration import ConfigurationABC
from cpl_core.dependency_injection import ServiceCollectionABC
from cpl_core.environment import ApplicationEnvironmentABC
from cpl_discord.service.discord_collection_abc import DiscordCollectionABC
from bot_core.abc.module_abc import ModuleABC
from bot_core.configuration.feature_flags_enum import FeatureFlagsEnum
from modules.permission.abc.permission_service_abc import PermissionServiceABC
from modules.permission.service.permission_service import PermissionService
class PermissionModule(ModuleABC):
def __init__(self, dc: DiscordCollectionABC):
ModuleABC.__init__(self, dc, FeatureFlagsEnum.permission_module)
def configure_configuration(self, config: ConfigurationABC, env: ApplicationEnvironmentABC):
pass
def configure_services(self, services: ServiceCollectionABC, env: ApplicationEnvironmentABC):
services.add_transient(PermissionServiceABC, PermissionService)
# commands
# events

View File

@ -0,0 +1,26 @@
# -*- coding: utf-8 -*-
"""
bot sh-edraft.de Discord bot
~~~~~~~~~~~~~~~~~~~
Discord bot for customers of sh-edraft.de
:copyright: (c) 2022 - 2023 sh-edraft.de
:license: MIT, see LICENSE for more details.
"""
__title__ = "modules.permission.service"
__author__ = "Sven Heidemann"
__license__ = "MIT"
__copyright__ = "Copyright (c) 2022 - 2023 sh-edraft.de"
__version__ = "1.2.2"
from collections import namedtuple
# imports
VersionInfo = namedtuple("VersionInfo", "major minor micro")
version_info = VersionInfo(major="1", minor="2", micro="2")

View File

@ -0,0 +1,74 @@
import discord
from cpl_core.configuration import ConfigurationABC
from cpl_core.logging import LoggerABC
from cpl_discord.service import DiscordBotServiceABC
from bot_data.abc.server_config_repository_abc import ServerConfigRepositoryABC
from bot_data.abc.server_repository_abc import ServerRepositoryABC
from bot_data.abc.technician_config_repository_abc import TechnicianConfigRepositoryABC
from bot_data.model.team_member_type_enum import TeamMemberTypeEnum
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class PermissionService(PermissionServiceABC):
def __init__(
self,
logger: LoggerABC,
bot: DiscordBotServiceABC,
config: ConfigurationABC,
servers: ServerRepositoryABC,
server_configs: ServerConfigRepositoryABC,
technician_configs: TechnicianConfigRepositoryABC,
):
PermissionServiceABC.__init__(self)
self._logger = logger
self._bot = bot
self._config = config
self._servers = servers
self._server_configs = server_configs
self._technician_configs = technician_configs
def _has_member_role(self, member: discord.Member, team_member_type: TeamMemberTypeEnum) -> bool:
if member is None or member.guild is None:
return False
self._logger.debug(__name__, f"Checking is member {member.name} {team_member_type.value}")
try:
server = self._servers.get_server_by_discord_id(member.guild.id)
config = self._server_configs.get_server_config_by_server(server.id)
roles = config.team_role_ids.where(lambda x: x.team_member_type == team_member_type).select(
lambda x: member.guild.get_role(x.role_id)
)
for role in roles:
if role not in member.roles:
continue
return True
except Exception as e:
self._logger.error(__name__, "Permission check failed", e)
return False
def is_member_admin(self, member: discord.Member) -> bool:
return self._has_member_role(member, TeamMemberTypeEnum.admin)
def is_member_moderator(self, member: discord.Member) -> bool:
return self._has_member_role(member, TeamMemberTypeEnum.moderator) or self._has_member_role(
member, TeamMemberTypeEnum.admin
)
def is_member_technician(self, member: discord.Member) -> bool:
if member is None or member.guild is None:
return False
self._logger.debug(__name__, f"Checking is member {member.name} technician")
try:
tech_config = self._technician_configs.get_technician_config()
if member.id in tech_config.technician_ids:
return True
except Exception as e:
self._logger.error(__name__, "Permission check failed", e)
return False

View File

@ -11,7 +11,7 @@ from bot_core.configuration.feature_flags_settings import FeatureFlagsSettings
from bot_core.helper.command_checks import CommandChecks
from bot_core.logging.command_logger import CommandLogger
from bot_data.model.server_config import ServerConfig
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
from modules.short_role_name.service.short_role_name_service import ShortRoleNameService

View File

@ -20,7 +20,7 @@ from bot_data.abc.api_key_repository_abc import ApiKeyRepositoryABC
from bot_data.abc.server_repository_abc import ServerRepositoryABC
from bot_data.abc.user_repository_abc import UserRepositoryABC
from bot_data.model.api_key import ApiKey
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class ApiKeyGroup(DiscordCommandABC):

View File

@ -1,4 +1,5 @@
import os
from string import Template
from zipfile import ZipFile
import discord
@ -17,7 +18,7 @@ from bot_core.abc.custom_file_logger_abc import CustomFileLoggerABC
from bot_core.abc.message_service_abc import MessageServiceABC
from bot_core.helper.command_checks import CommandChecks
from bot_core.logging.command_logger import CommandLogger
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class LogCommand(DiscordCommandABC):

View File

@ -13,7 +13,7 @@ from bot_core.helper.command_checks import CommandChecks
from bot_core.logging.command_logger import CommandLogger
from bot_core.service.data_integrity_service import DataIntegrityService
from bot_data.model.technician_config import TechnicianConfig
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class RestartCommand(DiscordCommandABC):

View File

@ -13,7 +13,7 @@ from bot_core.helper.command_checks import CommandChecks
from bot_core.logging.command_logger import CommandLogger
from bot_core.service.data_integrity_service import DataIntegrityService
from bot_data.model.technician_config import TechnicianConfig
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class ShutdownCommand(DiscordCommandABC):

View File

@ -20,7 +20,7 @@ from bot_data.model.server_config import ServerConfig
from bot_data.model.technician_config import TechnicianConfig
from bot_data.model.user import User
from modules.level.service.level_service import LevelService
from bot_core.abc.permission_service_abc import PermissionServiceABC
from modules.permission.abc.permission_service_abc import PermissionServiceABC
class SyncXpGroup(DiscordCommandABC):

View File

@ -128,17 +128,6 @@ export class Queries {
}
`;
static serverFeatureFlags = `
query HasServerFeatureFlag($filter: ServerFilter) {
servers(filter: $filter) {
featureFlags {
key
value
}
}
}
`;
static gameServerQuery = `
query GameServersList($serverId: ID) {
servers(filter: {id: $serverId}) {

View File

@ -1,7 +1,7 @@
import { GameServer, Server } from "../data/server.model";
import { User } from "../data/user.model";
import { AutoRole, AutoRoleRule } from "../data/auto_role.model";
import { Discord } from "../data/discord.model";
import { Discord, Guild } from "../data/discord.model";
import { Level } from "../data/level.model";
import { Achievement, AchievementAttribute } from "../data/achievement.model";
import { TechnicianConfig } from "../config/technician-config.model";
@ -82,10 +82,6 @@ export interface HasServerFeatureFlagQuery {
hasFeatureFlag: FeatureFlag;
}
export interface FeatureFlagsQuery {
featureFlags: FeatureFlag[];
}
export interface ShortRoleNameListQuery {
shortRoleNameCount: number;
shortRoleNames: ShortRoleName[];

View File

@ -113,7 +113,6 @@ export class MembersComponent extends ComponentWithTable implements OnInit, OnDe
{ label: this.translate.instant("common.bool_as_string.true"), value: false },
{ label: this.translate.instant("common.bool_as_string.false"), value: true }
];
this.spinner.hideSpinner();
this.loadNextPage();
});
}
@ -124,8 +123,7 @@ export class MembersComponent extends ComponentWithTable implements OnInit, OnDe
}
loadNextPage() {
if (!this.server?.id) return;
this.spinner.showSpinner();
this.loading = true;
this.data.query<UserListQuery>(Queries.usersQuery, {
serverId: this.server.id, filter: this.filter, page: this.page, sort: this.sort
@ -136,6 +134,7 @@ export class MembersComponent extends ComponentWithTable implements OnInit, OnDe
).subscribe(data => {
this.totalRecords = data.userCount;
this.members = data.users;
this.spinner.hideSpinner();
this.loading = false;
});
}

View File

@ -1,6 +1,6 @@
import { Injectable } from "@angular/core";
import { MenuItem } from "primeng/api";
import { BehaviorSubject } from "rxjs";
import { BehaviorSubject, forkJoin, Observable } from "rxjs";
import { AuthRoles } from "../../models/auth/auth-roles.enum";
import { AuthService } from "../auth/auth.service";
import { TranslateService } from "@ngx-translate/core";
@ -9,7 +9,7 @@ import { ThemeService } from "../theme/theme.service";
import { Server } from "../../models/data/server.model";
import { UserDTO } from "../../models/auth/auth-user.dto";
import { ServerService } from "../server.service";
import { FeatureFlagsQuery, Query } from "../../models/graphql/query.model";
import { HasServerFeatureFlagQuery, PossibleFeatureFlagsQuery, Query } from "../../models/graphql/query.model";
import { Queries } from "../../models/graphql/queries.model";
import { DataService } from "../data/data.service";
import { FeatureFlag } from "../../models/config/feature-flags.model";
@ -165,15 +165,31 @@ export class SidebarService {
if (server) {
this.featureFlags = [];
this.data.query<PossibleFeatureFlagsQuery>("{possibleFeatureFlags}"
).subscribe(data => {
let observables: Observable<HasServerFeatureFlagQuery>[] = [];
data.possibleFeatureFlags.forEach(flag => {
observables.push(
this.data.query<HasServerFeatureFlagQuery>(Queries.hasServerFeatureFlag, {
filter: { id: server.id },
flag: flag
},
function(data: Query) {
return data.servers[0];
}
)
);
});
this.data.query<FeatureFlagsQuery>(Queries.serverFeatureFlags, {
filter: { id: server.id }
},
function(data: Query) {
return data.servers[0];
}).subscribe(data => {
this.featureFlags = data.featureFlags;
this._setMenu(build);
forkJoin(observables).subscribe(data => {
data.forEach(flag => {
if (!flag.hasFeatureFlag.value) {
return;
}
this.featureFlags.push(flag.hasFeatureFlag);
});
this._setMenu(build);
});
});
} else {
this._setMenu(build);