Skip to main content
All configuration is supplied through environment variables. Copy .env.example to .env and fill in the values before starting the server. When DATABASE_URL is not set, the app uses an in-memory store — no database is required for local development or demos.
The following variables are production-critical. The application starts with the development defaults, but using them in production is a security risk.
  • JWT_SECRET — change from dev-secret-change-me before any real traffic
  • CAUSELOOP_MASTER_KEY — must be set when DATABASE_URL is set; encrypts all per-workspace data keys

Core server

Authentication — identity provider

AUTH_PROVIDER selects which upstream identity provider POST /auth/exchange verifies tokens against. It is pluggable — workos (the default, and what the Causeloop frontend uses via @workos-inc/authkit-nextjs), auth0, okta, oidc (generic), or none (no external provider — the dev fallback below).
With no AUTH_PROVIDER configured (or AUTH_PROVIDER=none), /auth/exchange falls back to a seed-user dev path — but only when ENVIRONMENT is not production. In production with no provider configured, exchange returns 503. See Local development for the dev-token flow.

LLM providers

Leave both API key variables empty to run in offline mock mode — the mock provider returns plausible stub responses and is suitable for local development and tests.

Database

For local Postgres: DATABASE_URL=postgresql://localhost:5432/causeloopFor Neon (hosted, SSL required): DATABASE_URL=postgresql://<user>:<pass>@<endpoint>.neon.tech/<db>?sslmode=require

Encryption

If DATABASE_URL is set but CAUSELOOP_MASTER_KEY is empty, the application will raise a KeyError_ on the first request that touches an encrypted column. Generate and store this secret securely before pointing the app at a real database.

Model provisioning & inference

Flags gating the provisioning portal, model lifecycle, and inference/queue subsystems. All are additive/rollback-safe: flipping any of these off does not delete data — it only stops a code path from running. A model already trained, evaluated, or hosted stays exactly as it was; only new activity is affected.
INFERENCE_PROFILE=prod and UPLOAD_STORE_URI=s3://... (Supabase Storage) are configuration paths, not proven capabilities — neither has been exercised against a live account in this environment. See Inference & Queue → Config-only paths before describing either as production-ready.

Frontend integration

Add these to your Next.js (or any frontend) .env.local:
For local development:
The API client reads the JWT from localStorage['causeloop_token'].

Full .env.example