The Authentik blueprint that provisions the OAuth2 Provider/Application only lived on CT121's filesystem via ad-hoc scp/pct push -- deploy/authentik/ is now the source of truth, with redeploy steps in docs/oidc-setup.md. Also documents two bugs found and fixed while implementing issue #19: the first RP-Initiated Logout attempt only ended the app-scoped session, and the provider had no property_mappings so the ID token's username claim was missing (fell back to a raw sub hash that looked like a leaked session token). Both are covered by new Playwright regression tests. The deep-check Fingerbank test now skips instead of failing when its target device (192.168.1.106) has since been manually labeled known via the dashboard, rather than assuming it stays unlabeled forever.
E2E tests
Playwright tests that drive a real browser against the live deployment
(https://monitor.jerodrigged.com by default) — not a local dev server or mocked
backend. They exist specifically because curl-based verification missed real bugs that
only show up with an actual browser (cookies, redirects, DOM interaction).
Setup
cd e2e
npm install
npx playwright install chromium
cp .env.example .env # fill in LOCAL_PASSWORD and OIDC_PASSWORD
npm test
OIDC_USERNAME/OIDC_PASSWORD should be the dedicated playwright-test Authentik
account (blueprint-provisioned on CT121, path users/service-accounts) — never a
real personal login. See docs/oidc-setup.md.
Not wired into CI
These hit the live production dashboard and a live Authentik instance, and need credentials as secrets — deliberately not run automatically on every push. Run by hand after auth-related changes.
Coverage
local-login.spec.ts— happy path (login/logout), wrong password rejected, session survives a page reload.oidc-login.spec.ts— happy path through a real Authentik login, wrong password rejected (stays on Authentik, never reaches the dashboard).api-auth.spec.ts—/api/hosts,/api/devices,/api/auth/meall reject unauthenticated requests; a failed login grants no access even though a session cookie gets issued (that's normal@fastify/sessionbehavior, not a leak — what matters is whether the cookie carries authentication, which it doesn't).
9 tests, confirmed stable across repeated full-suite runs with parallel workers.
Bugs these caught on first write (all fixed, kept as regression coverage)
- Local logout silently failed. Frontend always sent
Content-Type: application/jsoneven for logout's bodyless POST; Fastify's default JSON parser rejects that combination (400). curl testing missed it — curl doesn't set that header without-d. - OIDC login redirected to a LAN IP.
OIDC_ISSUER_URLused Authentik's internal address; its discovery document echoes back whichever host you query it through, so that LAN IP ended up as the browser-facingauthorization_endpoint. - OIDC token exchange rejected with
invalid_client. The callback handler hardcodedhttp://when reconstructing the current URL (Fastify never sees HTTPS — it terminates upstream), which sent the wrong scheme asredirect_uriin the token exchange. Authentik's own event log said plainly "Invalid redirect URI used by provider"; the error surfaced to the app as a genericinvalid_client.
None of these were caught by earlier curl-based verification — browser-driven auth flows (cookies, real redirect chains, a real IdP's login form) need a real browser.