Skip to content

Environment Variables

All configuration is passed to Kotauth via environment variables. Variables marked Required cause a fatal startup error if missing. Variables marked Recommended degrade functionality if absent but do not block startup.


Required.

The public base URL of the Kotauth instance. Used as the OIDC issuer (iss claim), in OIDC discovery documents, OAuth2 redirect URI validation, and email links.

KAUTH_BASE_URL=https://auth.yourdomain.com

Rules:

  • Must start with https:// when KAUTH_ENV=production. The server refuses to start otherwise.
  • HTTP is allowed for localhost in development mode.
  • No trailing slash.

Optional. Default: development

Controls startup validation strictness.

ValueBehavior
developmentHTTP allowed, startup warnings printed
productionHTTPS required, default JWT secret rejected, strict cookie flags enforced
KAUTH_ENV=production

Required.

A 32+ character hex string used for AES-256-GCM encryption (SMTP passwords, RSA private keys at rest), HMAC-SHA256 signing of short-lived cookies (MFA pending, PKCE verifier, portal session), and HMAC-SHA256 keying of the audit log integrity chain.

Terminal window
# Generate a key:
java -jar kauth.jar cli generate-secret-key
# Or manually:
openssl rand -hex 32
KAUTH_SECRET_KEY=<paste output here>

Supports file-based injection via KAUTH_SECRET_KEY_FILE. See File-based secrets below.


Optional. Default: false

When set to true, seeds two pre-configured workspaces with users, roles, groups, applications, webhooks, and audit history on startup. Renders a credential banner on all pages. Designed for public showcase deployments.

KAUTH_DEMO_MODE=true

Optional. Default: false

When set to true, Kotauth installs Ktor’s XForwardedHeaders plugin and trusts X-Forwarded-For and X-Forwarded-Proto headers from reverse proxies. This affects rate limiting (IP extraction) and HTTPS detection.

KAUTH_TRUSTED_PROXY=true

Optional.

Sets the password for the initial admin account (admin on the master tenant) created on first startup when the database is empty.

KAUTH_BOOTSTRAP_ADMIN_PASSWORD=YourStr0ng!Password

Validation rules: minimum 12 characters, at least one uppercase letter, one lowercase letter, and one digit. Failing validation causes a fatal startup error.

Behavior when not set:

  • In demo mode (KAUTH_DEMO_MODE=true): uses the demo password Demo1234!
  • In normal mode: generates a random password and prints it to stdout on first boot

Optional.

A JSON array of API keys to provision idempotently on startup. Useful for infrastructure-as-code and CI/CD pipelines.

KAUTH_BOOTSTRAP_API_KEYS='[{"tenant":"my-app","name":"ci-key","scopes":["users:read","users:write"],"keyHash":"sha256hex..."}]'

Each object in the array:

FieldRequiredDescription
tenantYesWorkspace slug
nameYesKey display name (upsert key — identifies the key)
scopesYesArray of scope strings
keyHashYesSHA-256 hex digest of the raw API key
keyPrefixNoDisplay prefix (default: kauth_{tenant} truncated to 16 chars)

Upsert behavior:

  • If no key with that (tenant, name) pair exists: created with enabled=true
  • If a key exists and hash + scopes match: no-op
  • If a key exists but hash or scopes differ: updated, re-enabled if previously disabled

Use java -jar kauth.jar cli hash-api-key to generate the SHA-256 hash for the keyHash field. See CLI Commands.


Kotauth connects to PostgreSQL using a standard JDBC URL. You can either provide the full URL directly via DB_URL, or let the compose stack construct it from the individual component variables.

Optional override.

Full PostgreSQL JDBC connection URL. When set, takes full precedence — DB_HOST, DB_PORT, and DB_NAME are ignored entirely.

Use this to connect to an external or managed database, or whenever you need to append JDBC parameters such as SSL mode:

DB_URL=jdbc:postgresql://your-host:5432/kotauth_db?sslmode=require

When DB_URL is not set, the bundled compose stack constructs it automatically from DB_HOST, DB_PORT, and DB_NAME.

See External Databases for provider-specific connection strings.


Optional. Default (in Docker Compose): db

Hostname of the PostgreSQL server. Used to construct the JDBC URL when DB_URL is not set.

# Bundled db service (default for local / Docker Compose)
DB_HOST=db
# External server
DB_HOST=xxx.rds.amazonaws.com

Optional. Default: 5432

Port of the PostgreSQL server. Used to construct the JDBC URL when DB_URL is not set.

DB_PORT=5432

Common non-default ports: 6432 for PgBouncer, 5433 for a non-standard local instance.


Optional. Default: 10

Maximum number of connections in the HikariCP pool.

DB_POOL_MAX_SIZE=10

Optional. Default: 2

Minimum idle connections maintained by HikariCP.

DB_POOL_MIN_IDLE=2

Optional. Default (in Docker Compose): kotauth_db

Database name. Used to construct the JDBC URL when DB_URL is not set, and to initialize the bundled db service.

DB_NAME=kotauth_db

Required.

PostgreSQL username.

DB_USER=kotauth

Required.

PostgreSQL password. As of v1.14.0, the server refuses to start if this is blank or missing — there is no fallback.

DB_PASSWORD=<strong password>

Optional.

Redis connection URL. When set, Kotauth uses Redis for distributed session storage and rate limiting instead of in-memory stores. Required for multi-instance deployments.

KAUTH_REDIS_URL=redis://localhost:6379

With authentication and TLS:

KAUTH_REDIS_URL=rediss://:your-password@redis-host:6380

See Redis for full setup instructions.


Optional. Default: 8

Maximum connections in the Lettuce connection pool.

KAUTH_REDIS_POOL_SIZE=8

Optional. Default: 3000

Connection and command timeout in milliseconds.

KAUTH_REDIS_TIMEOUT_MS=3000

Optional. Default: kotauth:

Prefix for all Redis keys. Useful when sharing a Redis instance with other services.

KAUTH_REDIS_KEY_PREFIX=kotauth:

Optional.

Redis authentication password. Used when the Redis instance requires authentication and you prefer to set the password separately rather than embedding it in KAUTH_REDIS_URL.

KAUTH_REDIS_PASSWORD=your-redis-password

Supports file-based injection via KAUTH_REDIS_PASSWORD_FILE. See File-based secrets below.


Optional.

Path to a directory containing JSON translation bundles. Each file should be named with a locale code (e.g. es.json, fr.json). When not set, only English is available.

KAUTH_I18N_BUNDLE_DIR=/i18n

See Internationalization for bundle format and Docker configuration.


Optional. Default: true

When true, Kotauth queries a version manifest on startup and surfaces available updates in the admin console. Set to false for air-gapped deployments.

KAUTH_UPDATE_CHECK=false

Optional.

Override the default version manifest URL. Useful for private registries or internal update servers. Must use https:// — the server refuses to start if an HTTP URL is provided. The HTTP client follows zero redirects, and releaseUrl values from the manifest are restricted to https:// schemes.

KAUTH_UPDATE_CHECK_URL=https://internal.example.com/kotauth/versions.json

Sensitive environment variables accept a *_FILE sibling that reads the value from a filesystem path at startup. The file contents are read and trimmed. When both <NAME> and <NAME>_FILE are set, the file value takes precedence.

Variable_FILE sibling
KAUTH_SECRET_KEYKAUTH_SECRET_KEY_FILE
DB_PASSWORDDB_PASSWORD_FILE
KAUTH_REDIS_PASSWORDKAUTH_REDIS_PASSWORD_FILE
KAUTH_BOOTSTRAP_ADMIN_PASSWORDKAUTH_BOOTSTRAP_ADMIN_PASSWORD_FILE
KAUTH_BOOTSTRAP_API_KEYSKAUTH_BOOTSTRAP_API_KEYS_FILE

Compatible with Docker Swarm secrets, Kubernetes mounted secrets, and systemd LoadCredential=. See Docker — File-based secrets for a compose example.


These variables are only used when running docker-compose.prod.yml (the Caddy TLS production compose). They are not read by Kotauth itself.

Required by docker-compose.prod.yml.

The public domain Caddy will serve and obtain a TLS certificate for.

DOMAIN=auth.yourdomain.com

Required by docker-compose.prod.yml.

Email address sent to Let’s Encrypt for certificate notifications.

ACME_EMAIL=you@yourdomain.com

These are not environment variables — they are configured per workspace through the admin console. Documented here for reference.

SettingDefaultNotes
Access token TTL300s (5 min)Configurable per application
Refresh token TTL86400s (24h)Workspace-wide
Email verification token24hFixed
Password reset token1hFixed
  • Minimum length (default: 8, range: 4–128)
  • Require uppercase / lowercase / numbers / symbols
  • Maximum age in days (0 = no expiry, range: 0–365)
  • Password history depth — prevent reuse of last N passwords (0 = no history check, range: 0–24)
  • Blacklist enabled — reject known-compromised passwords
  • Maximum failed attempts before lockout (default: 0 = disabled, range: 0–100)
  • Lockout duration in minutes (default: 15, range: 1–1440)
  • Admin can manually unlock users from the admin console
  • Locked users receive an email notification with a password reset link (requires SMTP)
ValueBehavior
optionalUsers can enroll but are not required to
requiredAll users must complete MFA before accessing the portal
required_for_adminsOnly users with the admin role are required to enroll
  • Host, port, username, password (AES-256-GCM encrypted at rest)
  • From address and display name
  • TLS mode: NONE, STARTTLS, or SSL

KAUTH_BASE_URL=http://localhost:8080
KAUTH_ENV=development
KAUTH_SECRET_KEY= # openssl rand -hex 32
DB_HOST=db
DB_PORT=5432
DB_NAME=kotauth_db
DB_USER=kotauth
DB_PASSWORD=changeme
KAUTH_BASE_URL=https://auth.yourdomain.com
KAUTH_ENV=production
KAUTH_SECRET_KEY= # openssl rand -hex 32
DB_HOST=db
DB_PORT=5432
DB_NAME=kotauth_db
DB_USER=kotauth
DB_PASSWORD= # strong unique password
DOMAIN=auth.yourdomain.com
ACME_EMAIL=you@yourdomain.com
KAUTH_BASE_URL=https://auth.yourdomain.com
KAUTH_ENV=production
KAUTH_SECRET_KEY= # openssl rand -hex 32
# DB_URL overrides DB_HOST / DB_PORT / DB_NAME
DB_URL=jdbc:postgresql://your-managed-host:5432/kotauth_db?sslmode=require
DB_USER=kotauth
DB_PASSWORD= # strong unique password

See External Databases for provider-specific examples.