mirror of
https://github.com/kevinveenbirkenbach/computer-playbook.git
synced 2026-11-06 10:59:59 +00:00
The OIDC admin wiring is gated on SSO alone, and SSO is 'web-app-keycloak' in group_names. Round 1 takes keycloak variant 1, which pins ldap off, so svc-db-openldap is not in the closure; the block still resolved its swarm service and the waiter spent 600 attempts on a service that does not exist (run 33698844864, Mattermost#1, 25 minutes). In compose the same block would have died on a missing container, so the defect is mode-independent.
The number it fetched is already in the registry: svc-db-openldap/tasks/04_users.yml:118 writes uidNumber from the same lookup('users'), and an earlier run shows inventory uid 1001 against ldapsearch 1001. Reading it directly removes the cross-stack exec entirely.
Keycloak's mattermost-id mapper reads the uidNumber attribute, which until now only the LDAP federation wrote, so the same round would have produced no id claim to match. ensure_realm_user.sh now mirrors the uid into that attribute whenever it is passed one, leaving callers without a uid unchanged.
Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
34 lines
1.3 KiB
YAML
34 lines
1.3 KiB
YAML
---
|
|
# Provision every non-reserved user directly in the Keycloak realm when LDAP is
|
|
# disabled. Without an LDAP federation this is the only path that seeds real
|
|
# end-user accounts (administrator, biber, ...); seeding only administrator left
|
|
# their SSO logins failing with user_not_found. Group memberships are applied
|
|
# afterwards by update/08_rbac_groups_realm.yml.
|
|
|
|
- name: "✅ Ensure non-reserved users exist in realm '{{ KEYCLOAK_REALM }}'"
|
|
ansible.builtin.script: shell/ensure_realm_user.sh
|
|
environment:
|
|
KEYCLOAK_EXEC_CONTAINER: "{{ KEYCLOAK_EXEC_CONTAINER }}"
|
|
KEYCLOAK_KCADM: "{{ KEYCLOAK_KCADM }}"
|
|
KEYCLOAK_REALM: "{{ KEYCLOAK_REALM }}"
|
|
KEYCLOAK_USERNAME: "{{ item.value.username }}"
|
|
KEYCLOAK_PASSWORD: "{{ item.value.password }}"
|
|
KEYCLOAK_EMAIL: "{{ item.value.email | default('') }}"
|
|
KEYCLOAK_FIRSTNAME: "{{ item.value.firstname | default('') }}"
|
|
KEYCLOAK_LASTNAME: "{{ item.value.lastname | default('') }}"
|
|
KEYCLOAK_USER_ENABLED: "true"
|
|
KEYCLOAK_UIDNUMBER: "{{ item.value.uid }}"
|
|
loop: >-
|
|
{{
|
|
lookup('users_non_reserved')
|
|
| dict2items
|
|
| selectattr('value.password', 'defined')
|
|
| selectattr('value.password')
|
|
| list
|
|
}}
|
|
loop_control:
|
|
label: "{{ item.value.username }}"
|
|
register: kc_realm_user_sync
|
|
changed_when: true
|
|
no_log: "{{ MASK_CREDENTIALS_IN_LOGS | bool }}"
|