"""System management mutations""" # pylint: disable=too-few-public-methods from typing import Optional import strawberry from selfprivacy_api.utils import pretty_error from selfprivacy_api.jobs.nix_collect_garbage import start_nix_collect_garbage from selfprivacy_api.graphql import IsAuthenticated from selfprivacy_api.graphql.common_types.jobs import job_to_api_job from selfprivacy_api.graphql.queries.providers import DnsProvider from selfprivacy_api.graphql.mutations.mutation_interface import ( GenericJobMutationReturn, GenericMutationReturn, MutationReturnInterface, ) import selfprivacy_api.actions.system as system_actions import selfprivacy_api.actions.ssh as ssh_actions from selfprivacy_api.actions.system import set_dns_provider @strawberry.type class TimezoneMutationReturn(MutationReturnInterface): """Return type of the timezone mutation, contains timezone""" timezone: Optional[str] @strawberry.type class AutoUpgradeSettingsMutationReturn(MutationReturnInterface): """Return type autoUpgrade Settings""" enableAutoUpgrade: bool allowReboot: bool @strawberry.type class SSHSettingsMutationReturn(MutationReturnInterface): """A return type for after changing SSH settings""" enable: bool password_authentication: bool @strawberry.input class SSHSettingsInput: """Input type for SSH settings""" enable: bool password_authentication: bool @strawberry.input class SetDnsProviderInput: """Input type to set the provider""" provider: DnsProvider api_token: str @strawberry.input class AutoUpgradeSettingsInput: """Input type for auto upgrade settings""" enableAutoUpgrade: Optional[bool] = None allowReboot: Optional[bool] = None @strawberry.type class SystemMutations: """Mutations related to system settings""" @strawberry.mutation(permission_classes=[IsAuthenticated]) def change_timezone(self, timezone: str) -> TimezoneMutationReturn: """Change the timezone of the server. Timezone is a tzdatabase name.""" try: system_actions.change_timezone(timezone) except system_actions.InvalidTimezone as e: return TimezoneMutationReturn( success=False, message=str(e), code=400, timezone=None, ) return TimezoneMutationReturn( success=True, message="Timezone changed", code=200, timezone=timezone, ) @strawberry.mutation(permission_classes=[IsAuthenticated]) def change_auto_upgrade_settings( self, settings: AutoUpgradeSettingsInput ) -> AutoUpgradeSettingsMutationReturn: """Change auto upgrade settings of the server.""" system_actions.set_auto_upgrade_settings( settings.enableAutoUpgrade, settings.allowReboot ) new_settings = system_actions.get_auto_upgrade_settings() return AutoUpgradeSettingsMutationReturn( success=True, message="Auto-upgrade settings changed", code=200, enableAutoUpgrade=new_settings.enable, allowReboot=new_settings.allowReboot, ) @strawberry.mutation(permission_classes=[IsAuthenticated]) def change_ssh_settings( self, settings: SSHSettingsInput ) -> SSHSettingsMutationReturn: """Change ssh settings of the server.""" ssh_actions.set_ssh_settings( enable=settings.enable, password_authentication=settings.password_authentication, ) new_settings = ssh_actions.get_ssh_settings() return SSHSettingsMutationReturn( success=True, message="SSH settings changed", code=200, enable=new_settings.enable, password_authentication=new_settings.passwordAuthentication, ) @strawberry.mutation(permission_classes=[IsAuthenticated]) def run_system_rebuild(self) -> GenericJobMutationReturn: try: job = system_actions.rebuild_system() return GenericJobMutationReturn( success=True, message="Starting system rebuild", code=200, job=job_to_api_job(job), ) except system_actions.ShellException as e: return GenericJobMutationReturn( success=False, message=str(e), code=500, ) @strawberry.mutation(permission_classes=[IsAuthenticated]) def run_system_rollback(self) -> GenericMutationReturn: system_actions.rollback_system() try: return GenericMutationReturn( success=True, message="Starting system rollback", code=200, ) except system_actions.ShellException as e: return GenericMutationReturn( success=False, message=str(e), code=500, ) @strawberry.mutation(permission_classes=[IsAuthenticated]) def run_system_upgrade(self) -> GenericJobMutationReturn: try: job = system_actions.upgrade_system() return GenericJobMutationReturn( success=True, message="Starting system upgrade", code=200, job=job_to_api_job(job), ) except system_actions.ShellException as e: return GenericJobMutationReturn( success=False, message=str(e), code=500, ) @strawberry.mutation(permission_classes=[IsAuthenticated]) def reboot_system(self) -> GenericMutationReturn: system_actions.reboot_system() try: return GenericMutationReturn( success=True, message="System reboot has started", code=200, ) except system_actions.ShellException as e: return GenericMutationReturn( success=False, message=str(e), code=500, ) @strawberry.mutation(permission_classes=[IsAuthenticated]) def pull_repository_changes(self) -> GenericMutationReturn: result = system_actions.pull_repository_changes() if result.status == 0: return GenericMutationReturn( success=True, message="Repository changes pulled", code=200, ) return GenericMutationReturn( success=False, message=f"Failed to pull repository changes:\n{result.data}", code=500, ) @strawberry.mutation(permission_classes=[IsAuthenticated]) def nix_collect_garbage(self) -> GenericJobMutationReturn: job = start_nix_collect_garbage() return GenericJobMutationReturn( success=True, code=200, message="Garbage collector started...", job=job_to_api_job(job), ) @strawberry.mutation(permission_classes=[IsAuthenticated]) def set_dns_provider(self, input: SetDnsProviderInput) -> GenericMutationReturn: try: set_dns_provider(input.provider, input.api_token) return GenericMutationReturn( success=True, code=200, message="Provider set", ) except Exception as e: return GenericMutationReturn( success=False, code=400, message=pretty_error(e), )