M2: SSSD LDAP identity + Kerberos login on nb (coexisting with local dominik) #269
Labels
No labels
bug
enhancement
in-progress
needs-info
needs-triage
p0
ready-for-agent
ready-for-human
wontfix
No milestone
No project
No assignees
1 participant
Notifications
Due date
No due date set.
Dependencies
No dependencies set.
Reference
Cloonar/nixos#269
Loading…
Add table
Add a link
Reference in a new issue
No description provided.
Delete branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Part of #266 (M2 of M1–M6). Follows #267, which is complete: the KDC on
mailis live,dominik.polakovics@CLOONAR.COMexists, andkinitreturns a TGT.Give
nban SSSD-backed LDAP identity whose login yields a Kerberos TGT, coexisting with the existing localdominikaccount rather than replacing it. Design context is indocs/adr/0022-keycloak-and-scoped-kerberos.md.The coexistence rule — this is the whole shape of the issue
users.users.dominikstays exactly as it is: uid 1000,/home/dominik, itshashedPassword, the ~570-linehosts/nb/users/dominik.nixhome-manager config, and all foursops.secrets.*.owner = "dominik"declarations (users/dominik.nix:171,174,modules/desktop/rustdesk.nix:41,modules/mcp-global.nix:79). The LDAP accountdominik.polakovics(uid 5001, gid 5001, home/home/dominik.polakovics) lands alongside it.The rename, the uid migration and the
chownsweep under/nix/persist/homeare deliberately deferred until SPNEGO is proven at M3. Do not start them here.Safety —
nbis the maintainer's daily laptopnbrunsnixos-rebuild switchunattended via bento every 5 minutes. A broken PAM stack locks the user out of their own machine.dominikauthenticating againstpam_unixwith its existinghashedPasswordmust keep working with SSSD stopped, misconfigured, or the network down.pam_sssrequired anywhere. NixOS orders itsufficientahead ofpam_unix; keep it that way so any SSSD failure falls through to local auth.security.pam.services.*entries that already exist beyond addingmakeHomeDirwhere noted.Scope
Create
hosts/nb/modules/ldap-login.nix(new) and import it fromhosts/nb/configuration.nix.Do not reuse
utils/modules/ldap-auth.nixIt is imported by
web-arm(hosts/web-arm/configuration.nix:29), so editing it puts a production host in the blast radius of a laptop change. It is also wrong fornbin three ways:services.openssh.settings.AuthorizedKeysCommand+AuthorizedKeysCommandUser = "nslcd"and creates annslcduser (ldap-auth.nix:59-77) — unwanted on a laptop.auth_provider = ldap;nbneedskrb5.Write a standalone module. Leave
utils/modules/ldap-auth.nixuntouched in this PR.SSSD configuration
services.sssd.kcm = trueso tickets land in the kernel keyring-backed KCM cache rather than a file, which is what survives a desktop session cleanly.cache_credentials = trueis required:nbroams, and the KDC is reachable only fromfwand over WireGuard. Off-VPN the user must still be able to log in from cache (with no TGT — that is expected, see ADR-0022 Consequences).sssd-environmentsecret inhosts/nb/secrets.yaml. Declaresops.secrets.sssd-environment = { };and wireservices.sssd.environmentFile. Same pattern asutils/modules/ldap-auth.nix:48.security.krb5client config onnbmirroringhosts/mail/modules/kerberos.nix(realmCLOONAR.COM, kdc/admin_servermail.cloonar.com,dns_lookup_realm/dns_lookup_kdcfalse,domain_realmforcloonar.comand.cloonar.com).Group schema — verify, do not copy blindly.
utils/modules/ldap-auth.nix:42-43setsldap_schema = rfc2307+ldap_group_member = memberUid, whilehosts/web-arm/modules/authelia.nix:77filters groups as(&(member={dn})(objectClass=groupOfNames))— those two descriptions of the directory disagree. Whichever is actually correct, the identity lookup demonstrably works onweb-armtoday, so mirror what works there for the id side and flag the group question in a comment rather than guessing. Supplementary-group resolution is a verification item below, not a blocker for login.PAM and home directory
security.pam.services.sddm.makeHomeDir = true.utils/modules/ldap-auth.nix:51-54coverslogin,sshd,sudoandsystemd-userbut notsddm, which isnb's actual display manager (hosts/nb/modules/desktop/default.nix:98). Without it the first graphical login has no home directory./homeis already persisted (hosts/nb/configuration.nix:169-174,directories = [ "/home" ]), so/home/dominik.polakovicssurvives reboots with no extra impermanence entry. Confirm, don't add a duplicate.enumerate = trueso SDDM lists the account in its user picker (showUsersByDefault = truein the theme). Upstream discourages enumeration on large directories; this one is small andweb-armalready does it. If it turns out SDDM still won't show the account, typing the username manually is an acceptable fallback — note it rather than fighting it.Browser SPNEGO policy
The
dominik.polakovicssession has no home-manager, so the policy must be system-level.Firefox needs
network.negotiate-auth.trusted-uris = .cloonar.com, expressed as an enterprise policy (Authentication.SPNEGO). Note the wrinkle:nbinstalls Firefox viaenvironment.systemPackages(hosts/nb/modules/desktop/default.nix:36), notprograms.firefox.enable, andprograms.firefox.policiesrequires the latter. Prefer droppingenvironment.etc."firefox/policies/policies.json"so nothing about the existing Firefox installation changes; switching toprograms.firefox.enableis acceptable only if the systemPackages entry is removed in the same change to avoid two Firefoxes in the closure. Verify which approach the installed build actually honours.Chromium/Chrome
AuthServerAllowlistis optional — add it only if a Chromium-family browser is already innb's package set.Out of scope
users.users.dominik, its uid, its home, or its home-manager config.chownsweep / uid migration / account rename (deferred past M3).utils/modules/ldap-auth.nixand anything onweb-armormail.dominik.polakovics; the test session is deliberately a bare desktop.wheel/sudo for the LDAP account — it should not have it.ADR
docs/adr/0022-keycloak-and-scoped-kerberos.mdalready covers M2. Amend it only if something here contradicts it — in which case say so explicitly rather than silently diverging.Verification
scripts/pre-commitdry-buildsnb. Do not runscripts/test-configurationmanually.Human, after deploy:
getent passwd dominik.polakovics→ uid 5001, home/home/dominik.polakovics.getent group 5001resolves.id dominik.polakovics— note whether supplementary LDAP groups appear (this is therfc2307-vs-groupOfNamesquestion above; primary group is what matters for login).dominikstill logs in with its own password before logging out.dominik.polakovicsSDDM entry using the Kerberos password set at #267.klistshowskrbtgt/CLOONAR.COM@CLOONAR.COM;echo $KRB5CCNAMEshows a KCM cache.Definition of done
hosts/nb/modules/ldap-login.nixexists and is imported;nbdry-builds clean.users.users.dominik,hosts/nb/users/dominik.nix,utils/modules/ldap-auth.nix, or any host other thannb.dominiklogin is provably unaffected by inspection of the PAM ordering.Closes #<this issue>.Heads-up for M3, since this issue is the spec a follow-on will copy from: the
sssd.confblock above haskrb5_store_password_if_no_ccache = true, which is not an SSSD option.It is absent from sssd 2.13's
src/config/cfg_rules.ini, andsss_ini_call_validators()'s return value is discarded inmonitor.c— so the daemon starts, logsAttribute 'krb5_store_password_if_no_ccache' is not allowed in section 'domain/cloonar.com'. Check for typos., and silently ignores the line. The offline→online TGT behaviour it was meant to give would never have happened.The real option is
krb5_store_password_if_offline(seesssd-krb5(5)), which is what #270 uses. Note the semantics differ slightly from the issue's comment: it is about caching the password while the provider is offline and requesting a TGT once the KDC is reachable again, not about "there is no ccache to put a ticket in yet".#270 also diverges on two other points where the spec could not work as written —
security.pam.services.sddm.makeHomeDirrenders no PAM rule (SDDM setsuseDefaultRules = false), andenumerate = truecannot surface in SDDM's picker on NixOS (NSS modules load only inside nsncd; the nscd protocol has no enumeration request, and SDDM usesgetpwent()). Both are explained in-file and in the PR description.