Stricter security. Moved to /auth/oidc/

This commit is contained in:
Leo Vasanko
2026-02-15 02:57:23 +00:00
parent b5a5f2707a
commit 701b0810bd
5 changed files with 61 additions and 49 deletions
+11 -11
View File
@@ -48,9 +48,9 @@ oid_auth_codes: dict[str, OIDAuthCode] = {}
- `GET /.well-known/openid-configuration` — Discovery document
- `GET /.well-known/jwks.json` — Public keys for token verification
### OIDC routes (`/auth/oid/`)
- `POST /auth/oid/token` — Token endpoint (code exchange)
- `GET /auth/oid/userinfo` — UserInfo endpoint (bearer token)
### OIDC routes (`/auth/oidc/`)
- `POST /auth/oidc/token` — Token endpoint (code exchange)
- `GET /auth/oidc/userinfo` — UserInfo endpoint (bearer token)
### Authorization (via existing restricted app)
- `GET /auth/restricted/?client_id=...&redirect_uri=...&response_type=code&scope=openid...`
@@ -58,8 +58,8 @@ oid_auth_codes: dict[str, OIDAuthCode] = {}
The restricted app detects OIDC params from URL and handles authentication via WebSocket.
## JWT & Signing
- RSA keypair generated on first boot (stored in data directory)
- ID tokens signed with RS256
- Ed25519 keypair generated on first boot (stored in data directory)
- ID tokens signed with EdDSA
- `kid` in JWKS for key rotation support
- Access tokens are signed JWTs (not opaque)
@@ -87,19 +87,19 @@ The `/auth/restricted/` page handles OIDC authorization alongside normal iframe
1. Client redirects to `/auth/restricted/?client_id=...&redirect_uri=...&response_type=code&scope=openid&state=...`
2. Frontend detects OIDC params from `window.location.search`
3. User authenticates via passkey
4. Frontend passes raw query string to `/auth/ws/authenticate?{query_string}`
3. Frontend passes raw query string to `/auth/ws/authenticate?{query_string}`
4. User authenticates via passkey
5. WebSocket validates client/redirect_uri, authenticates user, creates auth code
6. WebSocket returns `{"redirect_url": "redirect_uri?code=...&state=..."}`
7. Frontend redirects to the URL
8. Client exchanges code at `/auth/oid/token` → receives `id_token` + `access_token`
9. Optionally calls `/auth/oid/userinfo` with bearer token
8. Client exchanges code at `/auth/oidc/token` → receives `id_token` + `access_token`
9. Optionally calls `/auth/oidc/userinfo` with bearer token
**Key design points:**
- No session created during OIDC auth (stateless for the OIDC client)
- Raw query string preserved throughout (no parsing/reconstruction of redirect_uri)
- Redirect URI validated against client's registered URIs via exact string match
- PKCE supported (S256 and plain methods)
- PKCE required (S256 only)
## WebSocket OIDC Mode
@@ -124,7 +124,7 @@ When OIDC params absent:
- `paskia/db/structs.py` — Added `OIDClient`, `OIDAuthCode` models; User fields `email`, `preferred_username`
- `paskia/db/operations.py` — CRUD for OIDC entities
- `paskia/fastapi/oid.py` — Token and userinfo endpoints
- `paskia/util/oidjwt.py`RSA key management, JWT creation, JWKS
- `paskia/util/oidjwt.py`Ed25519 key management, JWT creation, JWKS
### Modified
- `paskia/fastapi/mainapp.py` — Mount OIDC app, well-known endpoints