apiVersion: v1 kind: ConfigMap metadata: name: authentik-blueprints namespace: authentik data: matrix-invitation-flow.yaml: | # yaml-language-server: $schema=https://goauthentik.io/blueprints/schema.json version: 1 metadata: name: matrix-invitation-flow labels: blueprints.goauthentik.io/instantiate: "true" entries: # Reaffirm the flow itself (already created manually; matched by slug) - model: authentik_flows.flow state: present identifiers: slug: matrix-invitation id: matrix_invitation_flow attrs: name: matrix-invitation title: matrix-invitation designation: enrollment # The prompt stage had accumulated 16 unrelated system validation_policies # (e.g. default-user-settings-authorization, default-oobe-password-usable) # from manual UI setup, likely a "select all" slip in the policy picker. # These crash on an anonymous enrollment context ('AnonymousUser' object # has no attribute 'group_attributes', etc). A prompt stage needs none here. - model: authentik_stages_prompt.promptstage state: present identifiers: name: matrix-invitation-prompt attrs: validation_policies: [] # Correct stage chain, mirroring the working matrix-enrollment flow: # Invite -> Prompt (username/email/password) -> Write -> Password -> Login # Root cause of the original bug: only Invite+Prompt were bound, both at # order=0, so the flow never wrote the user to the DB or logged them in. - model: authentik_flows.flowstagebinding state: present identifiers: target: !KeyOf matrix_invitation_flow order: 0 attrs: stage: !Find [authentik_stages_invitation.invitationstage, [name, matrix-enrollment-invitation]] - model: authentik_flows.flowstagebinding state: present identifiers: target: !KeyOf matrix_invitation_flow order: 1 attrs: stage: !Find [authentik_stages_prompt.promptstage, [name, matrix-invitation-prompt]] - model: authentik_flows.flowstagebinding state: present identifiers: target: !KeyOf matrix_invitation_flow order: 2 attrs: stage: !Find [authentik_stages_user_write.userwritestage, [name, default-source-enrollment-write]] - model: authentik_flows.flowstagebinding state: present identifiers: target: !KeyOf matrix_invitation_flow order: 3 attrs: stage: !Find [authentik_stages_password.passwordstage, [name, default-authentication-password]] - model: authentik_flows.flowstagebinding state: present identifiers: target: !KeyOf matrix_invitation_flow order: 4 attrs: stage: !Find [authentik_stages_user_login.userloginstage, [name, default-source-enrollment-login]] # Without an explicit destination, the flow falls back to Authentik's own # /if/user/ dashboard, which refuses type=external users ("Die Oberflaeche # kann nur von internen Nutzern geoeffnet werden") - exactly the user type # these Matrix-only accounts correctly have. Send them to Element instead. - model: authentik_stages_redirect.redirectstage state: present identifiers: name: matrix-invitation-redirect id: matrix_invitation_redirect_stage attrs: mode: static target_static: https://axion1337.chat - model: authentik_flows.flowstagebinding state: present identifiers: target: !KeyOf matrix_invitation_flow order: 5 attrs: stage: !KeyOf matrix_invitation_redirect_stage matrix-recovery-flow.yaml: | # yaml-language-server: $schema=https://goauthentik.io/blueprints/schema.json version: 1 metadata: name: matrix-recovery-flow labels: blueprints.goauthentik.io/instantiate: "true" entries: # matrix-recovery existed but had zero stage bindings (dead flow), and the # real login flow (default-authentication-flow, used by the MAS OAuth2 # provider's authentication_flow) didn't link to it at all - no "Forgot # password?" link was ever shown. Reuses the same default-recovery-* # stages the built-in default-recovery-flow already uses successfully, # plus our own redirect stage instead of falling back to the authentik # dashboard (blocked for type=external Matrix users). - model: authentik_flows.flow state: present identifiers: slug: matrix-recovery id: matrix_recovery_flow attrs: designation: recovery - model: authentik_flows.flowstagebinding state: present identifiers: target: !KeyOf matrix_recovery_flow order: 10 attrs: stage: !Find [authentik_stages_identification.identificationstage, [name, default-recovery-identification]] - model: authentik_flows.flowstagebinding state: present identifiers: target: !KeyOf matrix_recovery_flow order: 20 attrs: stage: !Find [authentik_stages_email.emailstage, [name, default-recovery-email]] - model: authentik_flows.flowstagebinding state: present identifiers: target: !KeyOf matrix_recovery_flow order: 30 attrs: stage: !Find [authentik_stages_prompt.promptstage, [name, "Change your password"]] - model: authentik_flows.flowstagebinding state: present identifiers: target: !KeyOf matrix_recovery_flow order: 40 attrs: stage: !Find [authentik_stages_user_write.userwritestage, [name, default-recovery-user-write]] - model: authentik_flows.flowstagebinding state: present identifiers: target: !KeyOf matrix_recovery_flow order: 100 attrs: stage: !Find [authentik_stages_user_login.userloginstage, [name, default-recovery-user-login]] - model: authentik_flows.flowstagebinding state: present identifiers: target: !KeyOf matrix_recovery_flow order: 110 attrs: stage: !Find [authentik_stages_redirect.redirectstage, [name, matrix-invitation-redirect]] # Wire the "Forgot password?" link on the real login flow used by MAS - model: authentik_stages_identification.identificationstage state: present identifiers: name: default-authentication-identification attrs: recovery_flow: !KeyOf matrix_recovery_flow matrix-mfa-setup-redirect.yaml: | # yaml-language-server: $schema=https://goauthentik.io/blueprints/schema.json version: 1 metadata: name: matrix-mfa-setup-redirect labels: blueprints.goauthentik.io/instantiate: "true" entries: # 2FA is optional (default-authentication-mfa-validation has # not_configured_action=skip - login never blocks on missing MFA). # Users who want to opt in use these built-in single-stage setup flows # directly (unreachable via /if/user/, which is blocked for type=external # Matrix accounts). Without a stage after the setup itself, completion # fell back to the same blocked /if/user/ dashboard - append our redirect. - model: authentik_flows.flowstagebinding state: present identifiers: target: !Find [authentik_flows.flow, [slug, default-authenticator-totp-setup]] order: 10 attrs: stage: !Find [authentik_stages_redirect.redirectstage, [name, matrix-invitation-redirect]] - model: authentik_flows.flowstagebinding state: present identifiers: target: !Find [authentik_flows.flow, [slug, default-authenticator-webauthn-setup]] order: 10 attrs: stage: !Find [authentik_stages_redirect.redirectstage, [name, matrix-invitation-redirect]] matrix-brand-default-app.yaml: | # yaml-language-server: $schema=https://goauthentik.io/blueprints/schema.json version: 1 metadata: name: matrix-brand-default-app labels: blueprints.goauthentik.io/instantiate: "true" entries: # Root cause behind several dead ends: an authenticated user hitting "/" # with no other destination (e.g. after logging in mid-way through the # TOTP/WebAuthn setup flows) falls back to Brand.default_application: if # unset, that's /if/user/, which type=external Matrix accounts can't # open. Only affects the bare "/" fallback - explicit URLs like # /if/admin/ are unaffected, so internal/staff access is unchanged. - model: authentik_brands.brand state: present identifiers: domain: authentik-default attrs: default_application: !Find [authentik_core.application, [slug, matrix]] # ThreadNet-Branding: Wer sich anmeldet, soll nicht auf einer Seite # landen, die sich "authentik" nennt und ein fremdes Logo zeigt. # Assets werden bewusst NICHT in Authentik hochgeladen, sondern von # der Client-Auslieferung referenziert - sie liegen dort ohnehin und # ein zweites Mal gepflegt zu werden ist genau die Quelle, aus der # spaeter Abweichungen entstehen. Ein ConfigMap-Mount scheidet aus: # die drei Dateien sind zusammen ~775 KB, base64-kodiert reissen sie # das 1-MiB-Limit einer ConfigMap. # # Preis dieser Wahl: faellt Element Web aus, zeigt die Anmeldeseite # Platzhalter statt Logo und Hintergrund. Kosmetisch, nicht # funktional - anmelden kann man sich weiterhin. # # ⚠️ alpenglow.jpg existiert erst nach dem naechsten Client-Deploy. # Wird diese Brand vorher ausgerollt, ist der Hintergrund 404 und # Authentik zeigt Grau. branding_title: ThreadNet branding_logo: https://axion1337.chat/vector-icons/512.png branding_favicon: https://axion1337.chat/vector-icons/favicon.ico branding_default_flow_background: https://axion1337.chat/themes/element/img/backgrounds/alpenglow.jpg matrix-oidc-provider.yaml: | # yaml-language-server: $schema=https://goauthentik.io/blueprints/schema.json version: 1 metadata: name: matrix-oidc-provider labels: blueprints.goauthentik.io/instantiate: "true" entries: # The OIDC Provider + Application linking Authentik to MAS was originally # clicked together by hand in the UI and existed nowhere as code (issue # #36): losing the Authentik DB would have meant re-creating this from # scratch, including a new client_secret that MAS would then no longer # match. client_secret is read from AUTHENTIK_MAS_OIDC_CLIENT_SECRET # (see authentik.yaml HelmRelease values) rather than inlined here, # since this ConfigMap itself is not SOPS-encrypted - the actual value # lives in the authentik-credentials Secret instead. - model: authentik_providers_oauth2.oauth2provider state: present identifiers: name: Matrix Authentication Service id: matrix_mas_provider attrs: client_type: confidential client_id: dHbTAgAgXvjh3VALh220mB3dxcVXAifiXU2ZO3U6 client_secret: !Env AUTHENTIK_MAS_OIDC_CLIENT_SECRET # Path includes MAS's own upstream-provider ID, not Authentik's - # must match MAS's config exactly or the OIDC callback breaks. redirect_uris: - matching_mode: strict url: https://account.axion1337.chat/upstream/callback/01KQDJTR1ZVTG8JQ220F5BNBFZ # Stable across username renames - this is what keeps # upstream_oauth_links rows valid after e.g. the elbojoloco rename. sub_mode: hashed_user_id include_claims_in_id_token: true access_code_validity: minutes=1 access_token_validity: minutes=5 signing_key: !Find [authentik_crypto.certificatekeypair, [name, "authentik Self-signed Certificate"]] authorization_flow: !Find [authentik_flows.flow, [slug, default-provider-authorization-implicit-consent]] invalidation_flow: !Find [authentik_flows.flow, [slug, default-provider-invalidation-flow]] property_mappings: - !Find [authentik_core.propertymapping, [managed, "goauthentik.io/providers/oauth2/scope-openid"]] - !Find [authentik_core.propertymapping, [managed, "goauthentik.io/providers/oauth2/scope-email"]] - !Find [authentik_core.propertymapping, [managed, "goauthentik.io/providers/oauth2/scope-profile"]] - model: authentik_core.application state: present identifiers: slug: matrix attrs: name: aXion1337.chat Accountverwaltung provider: !KeyOf matrix_mas_provider meta_description: Matrixclient tailored for aXionCommunity meta_publisher: aXionGaming policy_engine_mode: any open_in_new_tab: false