Environment Contract
Last reviewed: 2026-05-13
Maintained by: Engineering
This is the canonical list of environment variables used by the current setup.
Root API Runtime Variables
| Variable | Required | Example local value | Used for | GitHub storage |
|---|---|---|---|---|
NODE_ENV | yes | development | runtime mode | vars |
PORT | yes | 3000 | API port | vars |
DB_HOST | yes | localhost | DB connection | vars |
DB_PORT | yes | 5433 | DB connection | vars |
DB_NAME | yes | zgrid | DB connection | vars |
DB_USER | yes | postgres | DB connection | vars |
DB_PASSWORD | yes | postgres123 | DB connection | secrets |
DATABASE_URL | yes | postgresql://postgres:postgres123@localhost:5433/zgrid | DB connection / migrations | secrets |
JWT_ACCESS_SECRET | yes | dev-access-secret-change-me | access token signing | secrets |
JWT_REFRESH_SECRET | yes | dev-refresh-secret-change-me | refresh token config validation / auth hardening contract | secrets |
JWT_ACCESS_TTL | yes | 15m | access token TTL | vars |
JWT_REFRESH_TTL_DAYS | yes | 7 | refresh token TTL | vars |
WEB_ALLOWED_ORIGINS | yes | http://localhost:3001,http://127.0.0.1:3001 | CORS allow-list | vars |
COOKIE_SECURE | yes | false | auth cookie policy | vars |
COOKIE_SAME_SITE | yes | Lax | auth cookie policy | vars |
COOKIE_DOMAIN | no | empty | cross-subdomain cookie scope | vars |
EMAIL_PROVIDER | yes | dev_log locally, resend in staging/production | transactional email provider selection | vars |
EMAIL_FROM | yes when EMAIL_PROVIDER is not disabled | Zgrid <no-reply@zgrid.app> | transactional email sender | vars |
EMAIL_REPLY_TO | yes when EMAIL_PROVIDER is not disabled | support@zgrid.app | transactional email reply-to address | vars |
EMAIL_SUPPORT_ADDRESS | yes when EMAIL_PROVIDER is not disabled | support@zgrid.app | support contact shown in templates | vars |
EMAIL_ACTION_BASE_URL | yes when EMAIL_PROVIDER is not disabled | http://localhost:3001 | absolute base URL for email action links | vars |
MANAGER_DESK_URL | yes when EMAIL_PROVIDER is not disabled | http://localhost:3002 | Manager Desk origin and email URL fallback | vars |
RESEND_API_KEY | yes when EMAIL_PROVIDER=resend | not set locally | Resend API authentication for real delivery | secrets |
UPTIMEROBOT_API_KEY | no | empty | Back Office System Health uptime monitor checks | secrets |
UPTIMEROBOT_MONITOR_IDS | no | empty or 123,456 | Optional monitor filter for System Health uptime component | vars |
SENTRY_ENABLED | no | false locally, true in staging/production when DSN is present | API error monitoring toggle | vars |
SENTRY_DSN | no | empty locally | API Sentry DSN | secrets |
SENTRY_ENVIRONMENT | no | local, staging, production | API Sentry environment tag | vars |
SENTRY_RELEASE | no | api@2026.05.13 | API release tag for issue regression tracking | vars |
SENTRY_TRACES_SAMPLE_RATE | no | 0 locally, 0.1 in staging, 0.2 in production | API trace sampling | vars |
Manager Desk Runtime Variables
These values belong in apps/manager-desk/.env.local for local work and in the Manager Desk Vercel project settings for hosted environments.
| Variable | Required | Example local value | Used for | GitHub storage |
|---|---|---|---|---|
NEXT_PUBLIC_API_URL | yes | http://localhost:3000/api | Manager Desk API base URL | vars |
NEXT_PUBLIC_SENTRY_ENABLED | no | false locally, true when DSN is configured | Manager Desk browser error monitoring toggle | vars |
NEXT_PUBLIC_SENTRY_DSN | no | empty locally | Manager Desk browser Sentry DSN | vars |
NEXT_PUBLIC_SENTRY_ENVIRONMENT | no | local, staging, production | Manager Desk browser Sentry environment tag | vars |
NEXT_PUBLIC_SENTRY_RELEASE | no | manager-desk@2026.05.13 | Manager Desk browser release tag | vars |
NEXT_PUBLIC_SENTRY_TRACES_SAMPLE_RATE | no | 0 locally, 0.05 in staging, 0.1 in production | Manager Desk browser trace sampling | vars |
Back Office Runtime Variables
These values belong in apps/back-office/.env.local for local work and in the Back Office Vercel project settings for hosted environments.
| Variable | Required | Example local value | Used for | GitHub storage |
|---|---|---|---|---|
NEXT_PUBLIC_API_URL | yes | http://localhost:3000/api | Back Office API base URL | vars |
NEXT_PUBLIC_SENTRY_ENABLED | no | false locally, true when DSN is configured | Back Office browser error monitoring toggle | vars |
NEXT_PUBLIC_SENTRY_DSN | no | empty locally | Back Office browser Sentry DSN | vars |
NEXT_PUBLIC_SENTRY_ENVIRONMENT | no | local, staging, production | Back Office browser Sentry environment tag | vars |
NEXT_PUBLIC_SENTRY_RELEASE | no | back-office@2026.05.13 | Back Office browser release tag | vars |
NEXT_PUBLIC_SENTRY_TRACES_SAMPLE_RATE | no | 0 locally, 0.05 in staging, 0.1 in production | Back Office browser trace sampling | vars |
Zgrid Mobile Runtime Variables
These values belong in apps/zgrid-mobile/.env for local Expo work and in Expo/EAS project environment variables for hosted builds.
| Variable | Required | Example local value | Used for | GitHub storage |
|---|---|---|---|---|
EXPO_PUBLIC_API_URL | yes outside Expo fallback mode | http://127.0.0.1:3000/api | Mobile API base URL | n/a |
EXPO_PUBLIC_APP_ENV | no | development | Mobile runtime environment label | n/a |
EXPO_PUBLIC_EAS_PROJECT_ID | no | empty locally | Expo push token registration / EAS project binding | n/a |
EXPO_PUBLIC_ENABLE_RESIDENT_PAYMENTS | no | false | Resident payments feature flag | n/a |
EXPO_PUBLIC_SENTRY_ENABLED | no | false locally, true when DSN is configured | Mobile Sentry toggle | n/a |
EXPO_PUBLIC_SENTRY_DSN | no | empty locally | Mobile Sentry DSN | n/a |
EXPO_PUBLIC_SENTRY_ENVIRONMENT | no | local, staging, production | Mobile Sentry environment tag | n/a |
EXPO_PUBLIC_SENTRY_RELEASE | no | mobile@2026.05.13 | Mobile Sentry release tag | n/a |
EXPO_PUBLIC_SENTRY_TRACES_SAMPLE_RATE | no | 0 locally, 0.05 in staging, 0.1 in production | Mobile trace sampling | n/a |
Deploy-Only Variables
| Variable | Required | Used for | GitHub storage |
|---|---|---|---|
VERCEL_TOKEN | yes for deploy environments | Vercel CLI deploy | secrets |
VERCEL_ORG_ID | yes for deploy environments | Vercel project binding | secrets |
VERCEL_PROJECT_ID_MANAGER_DESK | yes for deploy environments | Manager Desk deploy target | secrets |
RAILWAY_TOKEN | historical / optional | legacy Railway CLI deploy wiring where still present | secrets |
RAILWAY_PROJECT_ID | historical / optional | legacy Railway project target wiring where still present | vars |
RAILWAY_ENVIRONMENT_ID | historical / optional | legacy Railway environment target wiring where still present | vars |
RAILWAY_SERVICE_ID_API | historical / optional | legacy Railway API service target wiring where still present | vars |
Environment Scope
Local
Local development uses:
.env.exampleas the template- root
.envas the actual local configuration apps/manager-desk/.env.exampleas the Manager Desk local templateapps/back-office/.env.exampleas the Back Office local templateapps/zgrid-mobile/.env.exampleas the mobile local template
Email rule for local development:
- use
EMAIL_PROVIDER=dev_log - do not add a real
RESEND_API_KEYlocally unless you intentionally want to test the real provider - local placeholders for sender/support addresses and action URLs are expected and should be replaced in staging/production
- keep all Sentry toggles disabled locally unless you intentionally want to verify Sentry delivery from your own machine
- a missing Sentry DSN must not block startup; the app should simply run without Sentry
Staging / Production
GitHub Actions expects the same variable names in:
StagingProduction
Important:
- deploy validation uses the same names as runtime
- there is no fallback mapping for required GitHub Environment values
- environment validation happens during manual deploy, not on every CI push
- staging/production must set
EMAIL_PROVIDER=resendand provide a realRESEND_API_KEY - staging/production can enable API Sentry with
SENTRY_ENABLED=trueplus a realSENTRY_DSN
Manager Desk hosted environments use Vercel project environment variables with the NEXT_PUBLIC_ names above.
Back Office hosted environments use Vercel project environment variables with the NEXT_PUBLIC_ names above.
Mobile hosted builds use Expo/EAS environment variables with the EXPO_PUBLIC_ names above.
Current docs standard note:
- API hosting in this portal is documented as
Render - Railway-related deploy variables above should be treated as historical or optional wiring, not the current hosting standard
Rules and Validation
Secrets
These values must not be committed to the repo:
- DB passwords
- JWT secrets
- deploy tokens
- Sentry DSNs should still be treated as environment-managed values and not hardcoded in source
Cookie Policy
If you use:
COOKIE_SAME_SITE=None
then this must also be true:
COOKIE_SECURE=true
Production Rules
Production startup must fail if:
JWT_ACCESS_SECRETis still set to the development placeholderJWT_REFRESH_SECRETis still set to the development placeholder
When You Change the Env Contract
If you add or change an environment variable, always update:
apps/api/src/config/env.ts.env.example- environment-contract.md
- ../04-operations/infrastructure.md
- GitHub Environment
vars/secretsforStagingandProductionif it is relevant to deploy
Sentry Notes
- session replay is intentionally not enabled in the current setup
- source map upload is intentionally deferred; add it only when the deploy pipeline is ready to handle Sentry auth and release publishing safely