Configuration
For the complete documentation index, see llms.txt. Prefer markdown by appending .md to documentation URLs or sending Accept: text/markdown.

Environment variables

How Edge Kit loads and validates configuration. Secrets in .env.local, public VITE_ values, wrangler.jsonc vars, and envin validation.

Edge Kit has a single environment schema, defined in env.config.ts at the repository root and validated with envin and Zod. Values come from three places:

  • Local secrets and overrides: .env.local (copied from .env.example). It's gitignored, so it's safe for sensitive values.
  • Non-secret config: the vars block of wrangler.jsonc. It's committed, and applies to deployed Workers.
  • Production secrets: stored in Cloudflare with wrangler secret put (or the dashboard), never in the repository.

One local secret file only

Wrangler prefers .dev.vars over .env and .env.local for the Worker env object. If both exist, values from .env.local never reach the Worker. Keep one of them.

Server and client variables

Variables are split by the VITE_ prefix:

  • VITE_* are public. Vite inlines them into the client bundle at build time, so never put secrets in them.
  • Everything else is server-only and is only readable on the Worker.
.env.local
# App
VITE_PRODUCT_NAME="TurboEdge"
VITE_URL="http://localhost:3000"
CONTACT_EMAIL="hello@turbostarter.dev"

# Auth
VITE_AUTH_PASSWORD="true"
VITE_AUTH_ANONYMOUS="true"
BETTER_AUTH_SECRET="<your-secret>"
BETTER_AUTH_URL="${VITE_URL}"

# Billing
STRIPE_SECRET_KEY="<your-stripe-secret-key>"
STRIPE_WEBHOOK_SECRET="<your-stripe-webhook-secret>"

...

Usage

In application code, read values through the validated config. Read server values only in server code; public values can also be used by the UI:

import env from "../../env.config.ts";

env.BETTER_AUTH_URL; // validated server variable
env.VITE_PRODUCT_NAME; // validated client variable

env.config.ts lives outside src/, so import it by relative path with the .ts extension.

Worker bindings

D1, KV, R2, Queues, and the other Cloudflare bindings come from import { env } from "cloudflare:workers" and are declared in wrangler.jsonc. Don't put binding IDs in env.config.ts.

Validation

The schema is checked when the app starts, so a missing or malformed variable fails fast with a readable error. Validation is skipped for postinstall, lint, cf-typegen, and generate-routes.

To bypass it temporarily (for example in a CI step that doesn't need real values), set SKIP_ENV_VALIDATION=1. To browse and check your setup visually, run:

pnpm env

Adding a variable

  1. Add it to the server or client block of env.config.ts with a Zod type.
  2. For VITE_ values, also map it in the env block from import.meta.env.
  3. Add a documented entry to .env.example.
  4. Set it in production with wrangler secret put <NAME> (secrets) or in vars (non-secrets).

Production

Secrets are set once per Worker:

pnpm wrangler secret put BETTER_AUTH_SECRET
pnpm wrangler secret put STRIPE_SECRET_KEY
pnpm wrangler secret put STRIPE_WEBHOOK_SECRET

Public VITE_* values are baked in at build time, so they must be available where pnpm build runs (for example in your CI). See the deployment guide for the full checklist.

How is this guide?

Last updated on

On this page

Ship globally on the edge. In minutes.Try Edge Kit