3.7 KiB
3.7 KiB
Auth Gateway Plan
Overview
Clojure-based edge gateway. All external traffic enters here. Authenticates requests, then proxies to internal services.
Stack
- http-kit (HTTP server + async reverse proxy)
- reitit (route matching to determine target service)
- Ring middleware (CORS, rate limiting, logging)
- next.jdbc + HoneySQL (via shared/) for session/token DB lookups
Responsibilities
- TLS termination (or sit behind nginx for TLS in prod)
- Token validation / session lookup (custom DB reads)
- Authorization (permission checks per route)
- Rate limiting (per-user, per-IP)
- Route authenticated requests to internal services:
/api/*→ API service/+ web routes → Web session manager/ws/tui/*→ TUI session manager/ws/mobile/*→ Mobile session manager (future)
- Session creation on login (custom DB writes)
- Audit logging
Auth Flow
OAuth Login (v1)
- Client redirects to
/auth/oauth/:provider(e.g.,/auth/oauth/github) - Auth GW redirects to provider's OAuth authorization URL
- Provider redirects back to
/auth/oauth/:provider/callbackwith auth code - Auth GW exchanges code for access token, fetches user profile from provider
- Auth GW creates/links user +
oauth_accountsrow, creates session in DB - Auth GW sets session cookie and redirects to app
Login Page
Auth GW owns the login page — Web SM never sees unauthenticated users. Renders a minimal page with OAuth provider buttons (GitHub, Gitea) and redirects to the appropriate SSO flow. After OAuth callback completes, Auth GW sets the session cookie and redirects back to the app.
Token Format
- Session tokens: 32 random bytes (256 bits of entropy), encoded as base64url
- Stored in DB as bcrypt hash (
token_hashcolumn insessionstable) - Client sends raw base64url token; Auth GW hashes and looks up the match
Session Lifecycle
- Rolling expiry: session TTL extends on each authenticated request
- Cookie attributes (web clients):
HttpOnly,Secure,SameSite=Strict - CLI/mobile: raw token in
Authorization: Bearer <token>header
Session Validation
- Client sends request with token (Authorization header or cookie)
- Auth GW hashes token with bcrypt, looks up
token_hashinsessions - If valid: extend expiry, attach user context headers (
X-User-Id,X-User-Role), proxy to target service - If invalid/expired: 401 response
First-User Bootstrap
On first server setup (no communities exist in DB):
- Auth GW login page shows a community creation form alongside OAuth buttons
- First user authenticates via OAuth, creates the initial community, becomes its owner
- After initial community exists, new users must be invited by an existing member (invite-only)
Future: Email-Based Local Auth
- Email + magic link or email + password (requires email infrastructure)
- Will add
credentialstable when implemented - OAuth remains primary, local auth is an alternative for self-hosted deployments
Request Routing
Auth GW generates a unique X-Trace-Id header on each inbound request.
All downstream services propagate the trace ID through the call graph.
Protocols Handled
- HTTPS: standard request/response proxy
- SSE: authenticate on initial connection, then pass through to session managers
TODO
- http-kit reverse proxy setup
- Route table: path prefix → internal service host:port
- Token/session DB schema (in shared/)
- Token validation middleware
- OAuth flow: GitHub provider (redirect → callback → session creation)
- OAuth flow: Gitea provider
oauth_accountstable: link OAuth identities to users- SSE connection authentication
- Rate limiting middleware
- Logout endpoint (delete session)
- CORS configuration
- Audit logging