Skip to main content

Configuration & Secrets

This guide documents all configuration options, environment variables, and recommended settings for Terragnos Core deployments.

Configuration Overview

Terragnos Core is configured via environment variables. Set these in your .env file, Docker Compose configuration, Kubernetes secrets, or your deployment platform's configuration system.

Required Configuration

Database

DATABASE_URL=postgres://user:password@host:5432/database

Format: PostgreSQL connection string
Required: Yes
Example: postgres://terragnos:secret@db:5432/terragnos

The database must have PostGIS extensions installed:

  • postgis
  • pgcrypto
  • uuid-ossp
  • pg_trgm

Authentication

AUTH_JWT_SECRET=your-secret-key-minimum-32-characters

Type: String
Required: Yes
Minimum length: 32 characters
Purpose: Secret key for JWT token signing and validation

Recommendation: Use a cryptographically random string. Generate with:

openssl rand -base64 32

Optional Configuration

Application Settings

# Port the API listens on
PORT=3000

# Node environment
NODE_ENV=production

# Logging level
LOG_LEVEL=info

LOG_LEVEL options: fatal, error, warn, info, debug, trace
Default: info

Authentication Settings

# Default tenant for tokens without tenant claim
AUTH_DEFAULT_TENANT=default

# JWT issuer (optional)
AUTH_JWT_ISSUER=your-issuer-name

# JWT audience (optional)
AUTH_JWT_AUDIENCE=your-audience-name

# Disable authentication (development only!)
AUTH_DISABLED=false

Warning: Never set AUTH_DISABLED=true in production.

Licensing

# License key from Terragnos
LICENSE_KEY=eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9...

# Public key for license verification
LICENSE_PUBLIC_KEY=-----BEGIN PUBLIC KEY-----...-----END PUBLIC KEY-----

# Encryption key for license storage
LICENSE_STORAGE_SECRET=optional-32-byte-key

LICENSE_STORAGE_SECRET: If provided, licenses are encrypted at rest in the database. Use a 32-byte random string.

Caching & Performance

# Redis connection for caching (optional)
REDIS_URL=redis://redis:6379

# Rate limiting: time window in seconds
RATE_LIMIT_TTL=60

# Rate limiting: max requests per window
RATE_LIMIT_LIMIT=120

# Layer cache TTL in seconds
LAYER_CACHE_TTL_SECONDS=3600

REDIS_URL: If not provided, the system uses in-memory caching (lost on restart).

RATE_LIMIT_TTL / RATE_LIMIT_LIMIT: Global rate limiting. Default: 120 requests per 60 seconds.

LAYER_CACHE_TTL_SECONDS: How long GeoJSON/MVT responses are cached. Default: 60 seconds (can be overridden per layer definition).

Event Stream

# Disable event stream (for testing/snapshots)
EVENT_STREAM_DISABLED=false

Set to true to disable the PostgreSQL LISTEN/NOTIFY event stream.

Configuration by Environment

Development

NODE_ENV=development
LOG_LEVEL=debug
AUTH_DISABLED=false
AUTH_JWT_SECRET=dev-secret-change-me
DATABASE_URL=postgres://terragnos:terragnos@localhost:5432/terragnos

Staging

NODE_ENV=production
LOG_LEVEL=info
AUTH_DISABLED=false
AUTH_JWT_SECRET=<strong-secret>
DATABASE_URL=<staging-database-url>
LICENSE_KEY=<staging-license>
LICENSE_PUBLIC_KEY=<staging-public-key>
REDIS_URL=redis://redis-staging:6379

Production

NODE_ENV=production
LOG_LEVEL=warn
AUTH_DISABLED=false
AUTH_JWT_SECRET=<production-secret>
DATABASE_URL=<production-database-url>
LICENSE_KEY=<production-license>
LICENSE_PUBLIC_KEY=<production-public-key>
LICENSE_STORAGE_SECRET=<encryption-key>
REDIS_URL=redis://redis-prod:6379
RATE_LIMIT_TTL=60
RATE_LIMIT_LIMIT=1000
LAYER_CACHE_TTL_SECONDS=7200

Secrets Management

Docker Compose

Use Docker secrets or .env files (never commit .env to version control):

services:
api:
env_file:
- .env
secrets:
- jwt_secret
- database_url

secrets:
jwt_secret:
file: ./secrets/jwt_secret.txt
database_url:
file: ./secrets/database_url.txt

Kubernetes

Use Kubernetes secrets:

apiVersion: v1
kind: Secret
metadata:
name: terragnos-secrets
type: Opaque
stringData:
AUTH_JWT_SECRET: your-secret
DATABASE_URL: postgres://...
LICENSE_KEY: ...

External Secret Managers

Integrate with:

  • AWS Secrets Manager
  • HashiCorp Vault
  • Azure Key Vault
  • Google Secret Manager

Configuration Validation

Terragnos Core validates configuration on startup. Invalid configuration causes the service to fail with a clear error message.

Common validation errors:

  • Missing DATABASE_URL
  • Invalid DATABASE_URL format
  • Missing AUTH_JWT_SECRET
  • Invalid REDIS_URL format (if provided)

Best Practices

  1. Use strong secrets – Minimum 32 characters, randomly generated
  2. Rotate secrets regularly – Update JWT secrets periodically
  3. Separate by environment – Use different secrets for dev/staging/prod
  4. Never commit secrets – Use .gitignore for .env files
  5. Use secret managers – Store secrets in dedicated secret management systems
  6. Limit access – Restrict who can view/modify secrets
  7. Monitor changes – Log secret rotations for audit trails
  8. Test configuration – Validate configuration in staging before production

Configuration Reference

VariableRequiredDefaultDescription
DATABASE_URLYes-PostgreSQL connection string
AUTH_JWT_SECRETYes-JWT signing secret (min 32 chars)
PORTNo3000API port
NODE_ENVNodevelopmentNode environment (development, test, production)
LOG_LEVELNoinfoLogging level (fatal, error, warn, info, debug, trace)
AUTH_DEFAULT_TENANTNodefaultDefault tenant ID
AUTH_JWT_ISSUERNo-JWT issuer claim (optional)
AUTH_JWT_AUDIENCENo-JWT audience claim (optional)
AUTH_DISABLEDNofalseDisable authentication (development only)
LICENSE_KEYNo-License key from Terragnos (JWT format)
LICENSE_PUBLIC_KEYNo-License verification key (RSA/PEM format)
LICENSE_STORAGE_SECRETNo-License encryption key (32-byte string)
REDIS_URLNo-Redis connection string (optional, for distributed caching)
RATE_LIMIT_TTLNo60Rate limit window (seconds)
RATE_LIMIT_LIMITNo120Max requests per window
LAYER_CACHE_TTL_SECONDSNo60Layer cache TTL (seconds)
EVENT_STREAM_DISABLEDNofalseDisable PostgreSQL LISTEN/NOTIFY event stream