Skip to main content

Configuration & secrets

Configuration splits cleanly into non-secret vars (in api/wrangler.toml [vars], reviewable in source) and secrets (set per environment via wrangler secret put, never committed). Frontend VITE_* values are public and ship in the browser bundle.

This page is a reference to where each value lives and what it does — it never lists secret values. The canonical credential list and how to obtain each key is SECRETS.md at the repo root; the deploy sequence is DEPLOYMENT.md.

Worker vars ([vars], non-secret)​

Set in api/wrangler.toml:

VarPurpose
ENVIRONMENTdev locally; production in prod (changes fail-closed behaviour — see below).
SERVICE_VERSIONSurfaced by /health (e.g. the git SHA in prod).
GEMINI_MODELAI model id (default gemini-3.1-flash-lite).
EMAIL_FROMSender address on the verified Resend domain.
PUBLIC_BASE_URLPublic origin for building survey/short links and Twilio callbacks.
CORS_ORIGINSComma-separated SPA origins allowed by CORS.
DEMO_TENANTDemo workspace client-account name (defaults to Black Cat Bank); blank disables the Cron demo top-up.

Worker secrets (wrangler secret put)​

Never in source, never in the bundle:

SecretUsed by
DATABASE_URLDirect Neon string — migrations, and the request path only when not using Hyperdrive.
RESEND_API_KEYEmail dispatch (invites, escalation/export delivery).
GEMINI_API_KEYAI (sentiment, coding) + STT.
CLERK_SECRET_KEYRequired. Clerk secret key — @clerk/backend uses it to verify session JWTs (fetches + caches the instance JWKS).
CLERK_JWT_KEYOptional PEM public key for fully networkless JWT verification (no Backend API round-trip).
CLERK_AUTHORIZED_PARTIESOptional comma-separated allowed azp (SPA) origins, for defence-in-depth.
TWILIO_ACCOUNT_SID / TWILIO_AUTH_TOKEN / TWILIO_FROMSMS/IVR (only when offered).
RESEND_WEBHOOK_SECRETVerifies inbound Resend delivery/open/click webhooks.
SENTRY_DSNWorker error tracking (when wired).

For the full provenance of each key (where to obtain it, which provider, rotation) see SECRETS.md.

Bindings (wrangler.toml)​

Not secrets, but infrastructure handles set in the toml — see Cloudflare topology:

  • HYPERDRIVE — the pooled Postgres path (preferred in prod).
  • R2_BUCKET — file-drop / export artefacts.
  • QUEUE_INGESTION (+ DLQ voc-ingestion-dlq) — the ingestion pipeline.

The queue producer adapter no-ops when its binding is absent, so capture stays synchronous and correct in local dev / tests until the queue is provisioned at deploy.

Frontend build vars (public)​

Set in the protovoc Workers Builds project's Build variables (and frontend/.env locally). All VITE_-prefixed → public:

VarPurpose
VITE_API_URLOptional public API origin; leave empty for the preferred same-origin front-door service binding.
VITE_CLERK_PUBLISHABLE_KEYClerk publishable key (pk_…); the ClerkProvider reads it to drive sign-in and org selection.
VITE_SENTRY_DSNOptional browser error tracking.

ENVIRONMENT=production fail-closed behaviour​

In production, provider webhooks fail closed: a webhook with a missing or unverifiable signature is rejected rather than processed. Outside production (ENVIRONMENT ≠ production) the verification path is relaxed so the endpoints can be exercised in local dev/tests without live provider secrets. Setting ENVIRONMENT=production is therefore a security-relevant flag, not just a label — it must be set for any internet-exposed deploy.