From 778065f46856fd4ea27a63fc64076b8ba33fca48 Mon Sep 17 00:00:00 2001 From: Jens Langhammer Date: Sun, 17 Apr 2022 16:52:55 +0200 Subject: [PATCH] core: add flag to globally disable impersonation Signed-off-by: Jens Langhammer --- authentik/api/v3/config.py | 3 +++ authentik/core/views/impersonate.py | 5 +++- authentik/lib/default.yml | 1 + schema.yml | 1 + web/src/pages/users/RelatedUserList.ts | 20 +++++++++++---- web/src/pages/users/UserListPage.ts | 20 +++++++++++---- web/src/pages/users/UserViewPage.ts | 29 ++++++++++++++-------- website/docs/installation/configuration.md | 8 ++++++ 8 files changed, 66 insertions(+), 21 deletions(-) diff --git a/authentik/api/v3/config.py b/authentik/api/v3/config.py index f74412fbc..74183e7b0 100644 --- a/authentik/api/v3/config.py +++ b/authentik/api/v3/config.py @@ -27,6 +27,7 @@ class Capabilities(models.TextChoices): CAN_SAVE_MEDIA = "can_save_media" CAN_GEO_IP = "can_geo_ip" + CAN_IMPERSONATE = "can_impersonate" class ErrorReportingConfigSerializer(PassiveSerializer): @@ -63,6 +64,8 @@ class ConfigView(APIView): caps.append(Capabilities.CAN_SAVE_MEDIA) if GEOIP_READER.enabled: caps.append(Capabilities.CAN_GEO_IP) + if CONFIG.y_bool("impersonation"): + caps.append(Capabilities.CAN_IMPERSONATE) return caps @extend_schema(responses={200: ConfigSerializer(many=False)}) diff --git a/authentik/core/views/impersonate.py b/authentik/core/views/impersonate.py index 96d66d4df..ed425a1ea 100644 --- a/authentik/core/views/impersonate.py +++ b/authentik/core/views/impersonate.py @@ -4,7 +4,7 @@ from django.http import HttpRequest, HttpResponse from django.shortcuts import get_object_or_404, redirect from django.views import View from structlog.stdlib import get_logger - +from authentik.lib.config import CONFIG from authentik.core.middleware import SESSION_IMPERSONATE_ORIGINAL_USER, SESSION_IMPERSONATE_USER from authentik.core.models import User from authentik.events.models import Event, EventAction @@ -17,6 +17,9 @@ class ImpersonateInitView(View): def get(self, request: HttpRequest, user_id: int) -> HttpResponse: """Impersonation handler, checks permissions""" + if not CONFIG.y_bool("impersonation"): + LOGGER.debug("User attempted to impersonate", user=request.user) + return HttpResponse("Unauthorized", status=401) if not request.user.has_perm("impersonate"): LOGGER.debug("User attempted to impersonate without permissions", user=request.user) return HttpResponse("Unauthorized", status=401) diff --git a/authentik/lib/default.yml b/authentik/lib/default.yml index a84e734d2..053e3caa2 100644 --- a/authentik/lib/default.yml +++ b/authentik/lib/default.yml @@ -72,3 +72,4 @@ default_user_change_username: true gdpr_compliance: true cert_discovery_dir: /certs default_token_length: 128 +impersonation: true diff --git a/schema.yml b/schema.yml index a9f72558b..2bc90ecc9 100644 --- a/schema.yml +++ b/schema.yml @@ -20087,6 +20087,7 @@ components: enum: - can_save_media - can_geo_ip + - can_impersonate type: string CaptchaChallenge: type: object diff --git a/web/src/pages/users/RelatedUserList.ts b/web/src/pages/users/RelatedUserList.ts index 7b11390ca..76d9fd4cb 100644 --- a/web/src/pages/users/RelatedUserList.ts +++ b/web/src/pages/users/RelatedUserList.ts @@ -7,10 +7,10 @@ import { until } from "lit/directives/until.js"; import PFAlert from "@patternfly/patternfly/components/Alert/alert.css"; import PFDescriptionList from "@patternfly/patternfly/components/DescriptionList/description-list.css"; -import { CoreApi, User } from "@goauthentik/api"; +import { CapabilitiesEnum, CoreApi, User } from "@goauthentik/api"; import { AKResponse } from "../../api/Client"; -import { DEFAULT_CONFIG, tenant } from "../../api/Config"; +import { DEFAULT_CONFIG, config, tenant } from "../../api/Config"; import { me } from "../../api/Users"; import { uiConfig } from "../../common/config"; import { PFColor } from "../../elements/Label"; @@ -143,9 +143,19 @@ export class RelatedUserList extends Table { - - ${t`Impersonate`} - `, + ${until( + config().then((config) => { + if (config.capabilities.includes(CapabilitiesEnum.Impersonate)) { + return html` + ${t`Impersonate`} + `; + } + return html``; + }), + )}`, ]; } diff --git a/web/src/pages/users/UserListPage.ts b/web/src/pages/users/UserListPage.ts index 2d082450c..43b4eae2f 100644 --- a/web/src/pages/users/UserListPage.ts +++ b/web/src/pages/users/UserListPage.ts @@ -7,10 +7,10 @@ import { until } from "lit/directives/until.js"; import PFAlert from "@patternfly/patternfly/components/Alert/alert.css"; import PFDescriptionList from "@patternfly/patternfly/components/DescriptionList/description-list.css"; -import { CoreApi, User } from "@goauthentik/api"; +import { CapabilitiesEnum, CoreApi, User } from "@goauthentik/api"; import { AKResponse } from "../../api/Client"; -import { DEFAULT_CONFIG, tenant } from "../../api/Config"; +import { DEFAULT_CONFIG, config, tenant } from "../../api/Config"; import { me } from "../../api/Users"; import { uiConfig } from "../../common/config"; import { PFColor } from "../../elements/Label"; @@ -149,9 +149,19 @@ export class UserListPage extends TablePage { - - ${t`Impersonate`} - `, + ${until( + config().then((config) => { + if (config.capabilities.includes(CapabilitiesEnum.Impersonate)) { + return html` + ${t`Impersonate`} + `; + } + return html``; + }), + )}`, ]; } diff --git a/web/src/pages/users/UserViewPage.ts b/web/src/pages/users/UserViewPage.ts index e94cd3c64..a4cd36d82 100644 --- a/web/src/pages/users/UserViewPage.ts +++ b/web/src/pages/users/UserViewPage.ts @@ -2,6 +2,7 @@ import { t } from "@lingui/macro"; import { CSSResult, LitElement, TemplateResult, html } from "lit"; import { customElement, property } from "lit/decorators.js"; +import { until } from "lit/directives/until.js"; import AKGlobal from "../../authentik.css"; import PFButton from "@patternfly/patternfly/components/Button/button.css"; @@ -15,9 +16,9 @@ import PFDisplay from "@patternfly/patternfly/utilities/Display/display.css"; import PFFlex from "@patternfly/patternfly/utilities/Flex/flex.css"; import PFSizing from "@patternfly/patternfly/utilities/Sizing/sizing.css"; -import { CoreApi, User } from "@goauthentik/api"; +import { CapabilitiesEnum, CoreApi, User } from "@goauthentik/api"; -import { DEFAULT_CONFIG } from "../../api/Config"; +import { DEFAULT_CONFIG, config } from "../../api/Config"; import { EVENT_REFRESH } from "../../constants"; import "../../elements/CodeMirror"; import { PFColor } from "../../elements/Label"; @@ -239,14 +240,22 @@ export class UserViewPage extends LitElement { ${t`Reset Password`} - + + ${until( + config().then((config) => { + if (config.capabilities.includes(CapabilitiesEnum.Impersonate)) { + return html` `; + } + return html``; + }), + )}