Self-hosting configuration
Every environment variable a self-hosted Gitterm reads, whether it is required, its default, and which ones you don't need.
This page lists every environment variable a self-hosted Gitterm deployment reads, for whoever configures the services. Each table says whether a variable is required, its default, and what it does. With Docker Compose you only fill in .env.selfhost (Docker Compose settings). On Railway, or with your own orchestration, set each service directly (Service variables). Variables for the hosted gitterm.dev service are listed under Not needed when self-hosting.
For the deploy steps, see Self-hosting.
Generate secrets
Generate each secret separately, with a different value for each:
openssl rand -hex 32This prints 64 hexadecimal characters. ENCRYPTION_MASTER_KEY must be exactly this format. What each secret protects and how to change it is on Security.
Docker Compose settings
docker-compose.selfhost.yml reads these from .env.selfhost and passes them to the right services. Compose stops with required variable ... is missing a value if a variable marked Yes is empty.
Only these names reach the containers. Adding any other variable to .env.selfhost has no effect unless you also add it to the service's environment in the Compose file.
Address and routing
Images
Database
Secrets and encryption
Admin account
Set both to create the first admin. Without them the admin step is skipped: there is no admin, and nobody can enable a provider.
GitHub
Set up the GitHub App, or a shared token, under Admin → Integrations. There are no environment variables for it. If an earlier version read GITHUB_APP_ID and GITHUB_APP_PRIVATE_KEY from the environment, save that App there once; the variables are no longer read.
Workspace pausing
Optional. Without a provider, emails are written to the server log.
Startup steps
The server image runs three steps before it starts, every time: migrations, the catalog seed (providers, agent types, images, models), and the admin seed. Each waits for the database and takes a lock, so several replicas can start at once. A failed step stops the server from starting.
Skip them only if you run the steps yourself, for example as a release job before you roll out new servers:
docker compose --env-file .env.selfhost -f docker-compose.selfhost.yml run --rm --no-deps --entrypoint sh server \
-c 'bun run /app/dist/scripts/migrate.mjs --prod && bun run /app/dist/scripts/seed.mjs --prod && bun run /app/dist/scripts/seed-admin.mjs'Service variables
Set these when you configure each service yourself, for example on Railway. Docker Compose sets them for you from the settings above; Compose: in a row says from which. Values marked Yes must be set: most fall back to gitterm.dev or localhost defaults that are wrong for your deployment.
Use the same value for a variable on every service that reads it.
server
listener
worker
The worker calls the server's internal API and reads no credentials, so it doesn't need the database or encryption settings.
web
The published web image replaces these when the container starts. If you build web yourself, for example with Railway's builder, they are fixed at build time: rebuild after you change one.
proxy
Not needed when self-hosting
These belong to the hosted service at gitterm.dev, or to development. Leave them unset, or at the value shown.
DEPLOYMENT_MODE and NEXT_PUBLIC_DEPLOYMENT_MODE must stay self-hosted. managed turns on billing and fails to start without the Polar settings.