fix(authentik): add minio policy scope mapping (homelab-admins->consoleAdmin else readonly) + set rock email — MinIO CLAIM_NAME=policy got no claim (no MinIO access); empty rock email broke Grafana OIDC (GitHub-style /emails 404)
This commit is contained in:
@@ -148,6 +148,28 @@ groups_mapping = get_or_create(
|
||||
)
|
||||
GROUPS_MAPPING_PK = groups_mapping["pk"]
|
||||
|
||||
# MinIO maps OIDC users to a MinIO policy via a "policy" claim
|
||||
# (MINIO_IDENTITY_OPENID_CLAIM_NAME=policy). Emit consoleAdmin (full admin) for
|
||||
# homelab-admins members, readonly for everyone else. Without this claim MinIO
|
||||
# assigns no policy and OIDC users get no access.
|
||||
_POLICY_EXPR = (
|
||||
"return {\"policy\": \"consoleAdmin\" "
|
||||
"if request.user.ak_groups.filter(name=\"homelab-admins\").exists() "
|
||||
"else \"readonly\"}"
|
||||
)
|
||||
policy_mapping = get_or_create(
|
||||
"/api/v3/propertymappings/provider/scope/",
|
||||
"/api/v3/propertymappings/provider/scope/",
|
||||
"scope_name=minio",
|
||||
{
|
||||
"name": "homelab: minio policy claim",
|
||||
"scope_name": "minio",
|
||||
"expression": _POLICY_EXPR,
|
||||
},
|
||||
patch_existing={"expression": _POLICY_EXPR},
|
||||
)
|
||||
POLICY_MAPPING_PK = policy_mapping["pk"]
|
||||
|
||||
# Fetch the standard openid/email/profile mapping pks (shipped by default).
|
||||
status, res = api("GET", "/api/v3/propertymappings/provider/scope/")
|
||||
by_scope = {m["scope_name"]: m["pk"] for m in res["results"]}
|
||||
@@ -182,6 +204,10 @@ if res.get("results"):
|
||||
status, rock = api("PATCH", f"/api/v3/core/users/{rock['pk']}/", {
|
||||
"groups": [homelab_admins["pk"], grafana_admins["pk"]],
|
||||
"is_active": True,
|
||||
# email is REQUIRED: Grafana's OIDC login reads the email claim from
|
||||
# userinfo; an empty email makes Grafana fall back to a GitHub-style
|
||||
# <userinfo>/emails call, which Authentik 404s -> login fails entirely.
|
||||
"email": "[email protected]",
|
||||
})
|
||||
if status not in (200, 201):
|
||||
die(f"PATCH user rock -> {status} {rock}")
|
||||
@@ -192,6 +218,8 @@ else:
|
||||
"username": "rock",
|
||||
"name": "Rock",
|
||||
"is_active": True,
|
||||
# Required for Grafana OIDC (see PATCH branch above).
|
||||
"email": "[email protected]",
|
||||
"groups": [homelab_admins["pk"], grafana_admins["pk"]],
|
||||
"path": "users",
|
||||
"type": "internal",
|
||||
@@ -258,6 +286,9 @@ SERVICES = {
|
||||
app_pks_for_binding = []
|
||||
|
||||
for name, cfg in SERVICES.items():
|
||||
# MinIO also needs the "policy" claim (via the minio scope mapping) so its
|
||||
# MINIO_IDENTITY_OPENID_CLAIM_NAME=policy maps homelab-admins -> consoleAdmin.
|
||||
provider_mappings = SCOPE_PKS + ([POLICY_MAPPING_PK] if name == "minio" else [])
|
||||
ns, secret_name, key = cfg["client_secret_source"]
|
||||
client_secret = kubectl_get_secret_key(ns, secret_name, key)
|
||||
if client_secret is None:
|
||||
@@ -284,7 +315,7 @@ for name, cfg in SERVICES.items():
|
||||
"authorization_flow": AUTHORIZATION_FLOW_PK,
|
||||
"invalidation_flow": INVALIDATION_FLOW_PK,
|
||||
"signing_key": SIGNING_KEY_PK,
|
||||
"property_mappings": SCOPE_PKS,
|
||||
"property_mappings": provider_mappings,
|
||||
"sub_mode": "hashed_user_id",
|
||||
"include_claims_in_id_token": True,
|
||||
# authentik 2026.x requires grant_types to be set explicitly; the
|
||||
@@ -301,7 +332,7 @@ for name, cfg in SERVICES.items():
|
||||
# never touch client_secret again once created (that's the source of
|
||||
# truth in the k8s Secret, and re-sending it here is harmless anyway).
|
||||
patch_existing={
|
||||
"property_mappings": SCOPE_PKS,
|
||||
"property_mappings": provider_mappings,
|
||||
"grant_types": ["authorization_code", "refresh_token"],
|
||||
"redirect_uris": [
|
||||
{"matching_mode": "strict", "url": u} for u in cfg["redirect_uris"]
|
||||
|
||||
Reference in New Issue
Block a user