Skip to content
VaultTerm
Browse docs

configuration-reference

Configuration overview

VaultTerm is entirely environment-driven: one image runs in dev, staging, or on-prem, and only the .env changes. This page covers where config lives and the production boot guards.

Updated Jun 23, 2026

VaultTerm is configured almost entirely through environment variables. There is one image and one codebase; the same build runs in local development, in staging, or on a customer’s own hardware. The only thing that differs between those environments is the .env file. There are no per-environment code branches and no hardcoded hosts, endpoints, or secrets baked into the build — everything that points at infrastructure is a variable you set, which is what makes the platform cloud-portable and safe to run air-gapped.

# A minimal self-hosted core
NODE_ENV=production
PORT=4000
APP_BASE_URL=https://vault.example.com
DATABASE_URL=postgres://vaultterm:[email protected]:5432/vaultterm
REDIS_URL=redis://cache.example.com:6379
JWT_SECRET=replace-with-a-long-random-secret-at-least-32-bytes
KEY_PROVIDER=local
DEV_MASTER_KEY=<64 hex chars>

Where configuration lives

For self-hosting, the canonical template is deploy/onprem/.env.example. Copy it to .env, fill in the values for your environment, and pass it to the container (Docker Compose reads it automatically; an air-gapped install mounts it). The template is the source of truth for every variable the platform reads — the reference pages below describe the subset a customer running their own instance legitimately sets, grouped by concern.

In development the server falls back to safe local defaults (a localhost API origin, a dev master key, a dev signing secret) so it boots with almost no configuration. Those defaults are explicitly not safe for production, which is what the boot guards below exist to enforce.

Production boot guards

When NODE_ENV=production, the server refuses to start in a knowingly-insecure state rather than booting with a weak default. Two guards matter most:

  • JWT secret guard. A weak, short, or dev-default JWT_SECRET is fatal under production. The secret must be at least 32 bytes and must not be the built-in development value. This prevents an instance from signing session tokens with a guessable key. See Authentication & sessions.
  • Private-network egress guard. Server-side outbound fetches to private, loopback, and cloud-metadata targets (RFC1918 ranges, 127.0.0.0/8, link-local metadata addresses) are blocked under production unless you explicitly set EGRESS_ALLOW_PRIVATE=1. This is an anti-SSRF control: a webhook URL, SSO endpoint, or AI provider that resolves to an internal address will be refused unless you have opted in because you genuinely run those services on a private network. See Core & database configuration.

Other production behaviors follow the same fail-closed principle — for example the Prometheus /metrics endpoint requires a token under production rather than serving openly. These are documented alongside the variables that control them on the reference pages.

Reference pages

The full variable reference is split by concern:

For the bigger picture, see Self-hosting overview and Architecture overview.