
Write-up und Proof-of-Concept für CVE-2026-94609, eine Privilegieneskalations-Schwachstelle in authentik, die es Benutzern mit add_user_to_group ermöglicht, über die Groups-API Superuser-Gruppen beizutreten.
Write-up und Proof-of-Concept für eine Privilege-Escalation-Schwachstelle in goauthentik/authentik, behoben in 2026.2.7 / 2026.5.7 / 2026.8.2 und zugewiesen als CVE-2026-94609 (GHSA-h6c5-mpvq-j4jc).
Ich war einer der genannten Melder dieses Advisories (
@anthonyk2923— Nennung akzeptiert). Dieses Repo dokumentiert den spezifischen Codepfad, den ich unabhängig gefunden und gemeldet habe, plus einen PoC. Das veröffentlichte Advisory deckt das vollständige, breitere Problem ab (Gruppenhierarchie + Rollenzuweisung), das von mehreren unabhängigen Forschern gemeldet und gemeinsam behoben wurde.
Ein Konto mit nur einer routinemäßigen, häufig delegierten Berechtigung —
authentik_core.add_user_to_group (Mitglieder zu einer Gruppe hinzufügen) —
konnte sich selbst oder jeden anderen Benutzer direkt in eine bestehende
Gruppe mit dem Flag is_superuser=True über die Standard-Groups-API
einfügen, und dieser Benutzer wurde sofort ein echter authentik-Superuser.
Dies geschah ohne jemals authentik_core.enable_group_superuser zu
besitzen, die Berechtigung, die speziell dafür gedacht ist, genau diese
Aktion abzusichern.
authentik hatte die spiegelbildliche Version dieses Bugs bereits auf der User-Seite behoben (Zuweisung von Superuser-Gruppen an einen Benutzer). Die entsprechende Prüfung fehlte auf der Group-Seite (Zuweisung von Benutzern zu einer Superuser-Gruppe).
authentik modelliert zwei bewusst getrennte RBAC-Berechtigungen für die Verwaltung der Gruppenmitgliedschaft:
authentik_core.add_user_to_group — gedacht für routinemäßige, delegierte
Mitgliederverwaltung (z. B. eine „Helpdesk"- oder „Teamleiter"-Rolle, die
alltägliche Teamzusammenstellungen verwaltet).authentik_core.enable_group_superuser — gedacht zur Absicherung der weit
sensibleren Handlung, eine Gruppe zu gewähren oder ihr beizutreten, deren
is_superuser=True-Flag jedes Mitglied zu einem vollwertigen
authentik-Superuser macht.Die Trennung existiert genau deshalb, damit eine Organisation die gewöhnliche Gruppenverwaltung breit delegieren kann, ohne gleichzeitig die Fähigkeit abzugeben, Superuser zu erzeugen.
authentik hatte diese exakte Verwechslung bereits einmal behoben, auf der
User-Seite der Beziehung (PATCH /api/v3/core/users/{pk}/ über
UserSerializer.validate_groups()), verfolgt als
GHSA-h6x7-hjjc-wjc9 / CVE-2026-40172
(CVSS 8.1, High). Der Fix fügte hinzu:
# authentik/core/api/users.py (fixed)
def validate_groups(self, groups: list) -> list:
"""Require enable_group_superuser permission when adding a user to a superuser group."""
...
for group in groups:
if not group.is_superuser:
continue
if group in current_groups:
continue
if not request.user.has_perm("authentik_core.enable_group_superuser"):
raise ValidationError(...)
Der symmetrische Codepfad auf der Group-Seite — Mitglieder zu einer Gruppe hinzufügen, statt Gruppen zu einem Benutzer hinzuzufügen — erhielt nie die entsprechende Prüfung.
GroupSerializer.validate_users() in authentik/core/api/groups.py prüfte
nur add_user_to_group und inspizierte self.instance.is_superuser
überhaupt nie:
# authentik/core/api/groups.py (vulnerable)
def validate_users(self, users: list) -> list:
"""Require add_user_to_group permission when adding new members via group PATCH."""
request: Request = self.context.get("request", None)
if not request:
return users
if not self.instance:
return users
current_user_pks = set(self.instance.users.values_list("pk", flat=True))
new_users = [u for u in users if u not in current_user_pks]
if not new_users:
return users
has_perm = request.user.has_perm(
"authentik_core.add_user_to_group"
) or request.user.has_perm("authentik_core.add_user_to_group", self.instance)
if not has_perm:
raise ValidationError(_("User does not have permission to add members to this group."))
return users
Es gibt in dieser Methode nirgends eine
if self.instance.is_superuser: require enable_group_superuser-Absicherung.
Infolgedessen:
Jeder Aufrufer, der
add_user_to_groupbesitzt — entweder global oder objektbezogen auf genau eine bestimmte Superuser-Gruppe — kann dasusers-Feld dieser Gruppe perPATCHändern, um jeden Benutzer (einschließlich sich selbst) hinzuzufügen, und dieser Benutzer wird sofort ein echter authentik-Superuser.
add_user_to_group ist genau die Art von Berechtigung, deren breite und von
enable_group_superuser unabhängige Delegierung authentiks eigenes
feingranulares RBAC-Modell fördert — z. B. an eine benutzerdefinierte Rolle
„Benutzermanager" oder „Helpdesk". Der bestehende Test
authentik/core/tests/test_groups_api.py::test_patch_users_with_global_perm
zeigte bereits, dass eine globale Gewährung von add_user_to_group (ohne
jegliche Objektbeschränkung) ausreicht, um Mitglieder per PATCH in jede
Gruppe der Instanz einzufügen — dieser Test übte jedoch nie eine Gruppe mit
is_superuser=True aus, sodass die Lücke unentdeckt blieb.
Dies ist derselbe zugrunde liegende Fehler, den das veröffentlichte Advisory breiter beschreibt: Gruppen bilden eine Hierarchie, und der Superuser-Status wird von jeder übergeordneten Gruppe geerbt, aber die Prüfungen, die absichern, wer die Gruppenmitgliedschaft, die Gruppenübergeordnung und die Rollenzuweisung ändern darf, suchten entweder überhaupt nicht nach dem Superuser-Status oder betrachteten nur das eigene Flag der Gruppe statt des effektiven (geerbten).
Vollständige Privilege Escalation von „jedem Konto, das eine routinemäßige, häufig delegierte Gruppenmitgliedschafts-Berechtigung besitzt" zu „vollwertigem authentik-Superuser" — der jeden Mandanten, das SSO jeder nachgelagerten Anwendung, jedes Benutzerkonto, alle von authentik verwalteten Secrets/Zertifikate und die gesamte Instanzkonfiguration kontrolliert.
CVE-2026-94609.py
Ein eigenständiger PoC im Stil eines Live-HTTP-Clients. Er nimmt eine
Ziel-URL und ein API-Token für ein Konto mit geringen Rechten (das nur
add_user_to_group besitzt) sowie optional eine Zielgruppe/ein Opfer
entgegen und versucht dann dieselbe Eskalation über die echte API:
# Check your own deployment for the bug, no mutation:
python3 exploit_CVE-2026-94609.py --url https://authentik.example.com \
--token <low-priv-api-token> --group "superadmins" --check-only
# List superuser groups reachable to this token:
python3 exploit_CVE-2026-94609.py --url https://authentik.example.com \
--token <low-priv-api-token> --list-groups
# Attempt the actual escalation (self, or a named/PK victim):
python3 exploit_CVE-2026-94609.py --url https://authentik.example.com \
--token <low-priv-api-token> --group "superadmins" --victim jdoe
Erfordert nur pip install requests. Nur zur autorisierten Nutzung —
führe dies gegen Instanzen aus, für deren Test du ausdrücklich autorisiert
bist.
| Branch | Betroffen | Gepatcht |
|---|---|---|
| 2026.2.x | ≤ 2026.2.6 | 2026.2.7 |
| 2026.5.x | ≤ 2026.5.6 | 2026.5.7 |
| 2026.8.x | ≤ 2026.8.1 | 2026.8.2 |
Aktualisiere auf eine gepatchte Version. Wenn du nicht sofort aktualisieren kannst, beschränke gemäß dem Workaround des offiziellen Advisories die Berechtigungen zum Erstellen/Ändern von Gruppen, zum Ändern von Benutzern und zum Hinzufügen von Benutzern zu Gruppen so, dass nur vollständige Administratoren sie besitzen — delegiere keine dieser Berechtigungen an Nicht-Admin-Rollen, bis gepatcht wurde.
Dieses Write-up und der PoC werden für Bildungs- und defensive Sicherheitsforschungszwecke bereitgestellt. Siehe authentiks eigene Lizenz (MIT) für das zugrunde liegende Projekt.
| Schwachstellenklasse | Privilege Escalation / Improper Access Control |
| CWE | CWE-269 (Improper Privilege Management), CWE-863 (Incorrect Authorization) |
| CVSS 3.1 | AV:N/AC:L/PR:L/UI:N/S:U/C:H/I:H/A:H — High |
| Betroffen | authentik ≤ 2026.2.6, ≤ 2026.5.6, ≤ 2026.8.1 |
| Behoben in | 2026.2.7, 2026.5.7, 2026.8.2 |
| Erreichbare Route | PATCH /api/v3/core/groups/{group_uuid}/ |
| Ursache | GroupSerializer.validate_users() prüfte nie enable_group_superuser |