Commit graph

14 commits

Author SHA1 Message Date
Johan Lundberg
c175633980
fix(security): POST WebAuthn login-begin; render JS errors as text
Two WebAuthn client/route hardening fixes:

- GET /login/webauthn/begin wrote a challenge to the session on a safe method
  (login-flow DoS / CSRF surface). Make it POST with CSRF, matching the
  registration-begin endpoint; update webauthn.js and tests accordingly.

- webauthn.js rendered dynamic error text (err.message, server error fields)
  via innerHTML — an XSS-prone sink. Add showAlert() that sets textContent;
  route all dynamic error messages through it. The trusted server-rendered
  credentials partial is still injected as markup.

Refs: porchlight-cog, porchlight-t7y

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-05 14:04:24 +02:00
Johan Lundberg
baef5e0e2e
fix(security): require CSRF-protected POST to consume a registration link
GET /register/{token} consumed the magic-link token and created a session, so
a side-effecting state change happened on a safe method — link prefetchers,
email scanners, or a cross-site GET could trigger account setup/login.

Split the flow: GET validates the token (without consuming) and renders a
confirmation form; POST /register/{token} consumes the token, runs the
existing checks, and establishes the session. The POST carries a CSRF token
and the session is reset on login as for other auth paths.

Refs: porchlight-9k0

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-05 13:40:30 +02:00
Johan Lundberg
407db57279
fix(security): reset session on login to prevent fixation
Both password and WebAuthn login wrote the authenticated identity onto the
existing pre-auth session, so a fixed/planted session could be elevated to an
authenticated one. Add _establish_authenticated_session() which clears the
session (preserving only a pending OIDC authorization request) before setting
the identity, used by both login paths.

Tests that reused a pre-login CSRF token now re-fetch it after login, matching
real client behavior.

Refs: porchlight-vxr

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-04 14:23:08 +02:00
Johan Lundberg
faeecaed59
fix(security): invite links must not log in accounts with credentials
A registration/re-invite link auto-established a session for any existing
active user, so re-inviting a fully set-up user acted as a passwordless
login. Invite links are for account setup only.

After consuming the token, refuse to establish a session when the target
account already has a password or WebAuthn credential. Credential-less
accounts (e.g. freshly created by initial-admin) can still complete setup.
Account recovery for set-up accounts must use a separate, authenticated flow.

Refs: porchlight-a3a

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-04 10:51:01 +02:00
Johan Lundberg
91a2277664
fix(security): store only a hash of magic-link tokens
Magic-link tokens were persisted in plaintext, so a database read disclosed
usable login/invite tokens. The service now hashes tokens (HMAC-SHA256 when a
pepper is configured, else SHA-256 of the high-entropy token) and persists
only the hash; the raw token is exposed solely in the registration URL and is
re-attached to objects returned to callers.

Refs: porchlight-42h

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-04 10:36:18 +02:00
Johan Lundberg
a65af90320
feat: require current password when changing password, add zxcvbn strength check
Use PasswordChange model (requires current password) for users with
existing passwords and PasswordSet for first-time setup. Add zxcvbn
strength validation and current password field to credentials template.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-03-31 15:34:43 +02:00
Johan Lundberg
1054feb534
fix: reorder imports and use ty-compatible type suppression 2026-02-19 14:29:01 +01:00
Johan Lundberg
f648422227
test: update all tests to include CSRF tokens 2026-02-19 14:19:47 +01:00
Johan Lundberg
80960d5a1f
Merge branch 'feature/cli-module' 2026-02-18 11:35:15 +01:00
Johan Lundberg
1c21d6d199
test: add failing test for registering pre-existing users
Part of CLI module work (fastapi-oidc-op-9lb.1). The test verifies that
/register/{token} handles users already created by initial-admin.
2026-02-17 14:09:00 +01:00
Johan Lundberg
cd9469342b
refactor: fix lint warnings in webauthn login tests 2026-02-17 13:46:02 +01:00
Johan Lundberg
32567b5484
feat: rewrite WebAuthn login routes for usernameless discoverable credential flow 2026-02-17 13:38:17 +01:00
Johan Lundberg
7cb1adbd06
update all imports in test files: fastapi_oidc_op → porchlight 2026-02-16 15:34:53 +01:00
Johan Lundberg
e15dcc4745
feat: add authentication routes with session login, WebAuthn, and credential management
Implement Phase 4 auth routes: password login/logout, WebAuthn
registration and authentication, magic link registration, and
credential management pages with HTMX. Includes session middleware,
Jinja2 templates, vendored HTMX, and last-credential guardrails.

120 tests passing.
2026-02-16 11:39:50 +01:00