Awwwth Identity
Awwwth is a self-hosted identity service built with Bun, TypeScript, and PostgreSQL. It can use Keycloak for credentials and sign-in while keeping its own account management interface, company permissions, sessions, and OAuth/OpenID Connect issuer for applications.
Features
- Keycloak authentication through authorization-code flow with S256 PKCE, a branded login theme, encrypted upstream tokens, and back-channel logout.
- Email/password registration, email verification, and password recovery.
- Authenticator MFA, recovery codes, and WebAuthn passkeys.
- Profiles, phone numbers, saved addresses, sessions, connected applications, and account activity.
- Company-specific account directories and owner-managed applications and users.
- Platform administration for user status, deletion, and application registration.
- Authorization-code flow with S256 PKCE, signed ID tokens, token introspection, rotating refresh tokens, and queued back-channel logout.
- Resend, sendmail, or local email spooling; optional OpenTelemetry traces.
Add Awwwth to another application
The awwwth CLI adds an authentication gateway to any HTTP backend. Apps connected to the same account directory reuse the central sign-in session, so opening a second app signs in the same user without another password prompt. The public package is available with npx awwwth. See the guides below for installation, the two-app walkthrough, and npm releases.
Documentation
Read the documentation index, or open /docs on your running Awwwth server. The public documentation frontend renders these same Markdown guides and does not require sign-in.
| Guide | Contents |
|---|---|
| CLI installation | Install the published package and integrate your backend |
| Shared sign-in | Two-app walkthrough, session behavior, and logout |
| Package releases | Test, publish, verify, and troubleshoot npm releases |
| Configuration | Environment variables, secrets, origins, and email |
| Keycloak | Keycloak authentication behind your Awwwth layer |
| Architecture | Source layout, data model, authentication, and background jobs |
| API reference | Account, company, administrator, and OAuth endpoints |
| Application integration | Client registration, OIDC flow, browser SDK, and logout |
| Operations | Production deployment, health checks, upgrades, and troubleshooting |
Run with Keycloak
Follow the Keycloak setup guide to start the complete local stack. Applications and branded sign-in both use http://localhost:4100; Keycloak runs behind Awwwth. The administrator console is available separately on loopback at http://localhost:8080/admin/. The guide covers client secrets, verified users, existing account migration, and production configuration.
Native backend quick start with Docker
Install Docker with Compose, then run from the repository root:
docker compose up -d --build
docker compose ps
docker compose logs --tail 100 app
Open <http://localhost:4100>. Compose creates PostgreSQL, applies migrations, generates persistent keys, and starts the application. The base configuration uses development credentials and local email spooling.
Register an account in the browser. Development verification and reset emails are written as .eml files inside the app container:
docker compose exec app ls /app/.local/mail
Read a listed file with docker compose exec app cat /app/.local/mail/FILE.eml, replacing FILE.eml with its actual filename.
To grant platform administrator access to an existing active platform account:
docker compose exec app bun run admin account@example.com
The base Compose file does not publish PostgreSQL to the host. See Operations for production deployment, which uses the OCI override and HTTPS.
Run directly with Bun
Requirements: Bun 1.4.0 or later, plus a reachable PostgreSQL database. The container configuration uses PostgreSQL 18.
bun install --frozen-lockfile
cp .env.example .env
bun run setup
Edit .env for local development:
NODE_ENV=development
HOST=127.0.0.1
PORT=4100
AUTH_ORIGIN=http://localhost:4100
AUTH_API_ORIGIN=http://localhost:4100
DATABASE_URL=postgres://awwwth:replace-with-password@localhost:5432/awwwth_auth
SIGNING_KEY_PATH=.local/keys/signing.pem
MAIL_MODE=spool
AUTH_BACKEND=native
Set ENCRYPTION_KEY in .env to the exact contents of .local/keys/encryption.key. Create the database and database user separately, and adjust DATABASE_URL to match. Setup generates keys only; it does not provision PostgreSQL or populate .env.
To use Keycloak instead, set AUTH_BACKEND=keycloak and configure the realm and confidential client using the Keycloak guide.
bun run migrate
bun run build
bun start
Bun loads the local environment file. Spool emails appear in .local/mail. Rebuild after stylesheet changes and restart after source changes; start does not enable watch mode. Keep .env, private keys, and spool emails private.
Commands
| Command | Purpose |
|---|---|
bun run setup | Create missing encryption and signing keys, then validate them |
bun run migrate | Apply pending SQL migrations in filename order |
bun run typecheck | Check TypeScript without emitting files |
bun run css:build | Generate minified dist/tailwind.css |
bun run build | Run type checking and the stylesheet build |
bun start | Start the HTTP server and background worker |
bun run admin <email> | Grant administrator access to an existing active platform account |
Browser JavaScript and the SDK are bundled at server startup. Use bun run test for CLI/security tests and bun run test:sso for the PostgreSQL-backed two-app integration test. There is no lint script.