Environment Variables

Quick Start - Minimum for Local Development

To get the API and UI running locally, you need a surprisingly small set of variables. Copy .env.example to .env at the repo root and fill in these essentials:

Terminal window
# Database
DATABASE_URL=postgresql://postgres:postgres@localhost:5432/autonoma
# Redis
REDIS_URL=redis://localhost:6379
# API server
API_PORT=4000
SCENARIO_ENCRYPTION_KEY=any-string-at-least-1-char
# Google OAuth (create credentials at console.cloud.google.com)
GOOGLE_CLIENT_ID=your-google-client-id
GOOGLE_CLIENT_SECRET=your-google-client-secret
# AI model keys (needed for test execution)
GEMINI_API_KEY=your-gemini-key
GROQ_KEY=your-groq-key
OPENROUTER_API_KEY=your-openrouter-key
# S3-compatible storage (can use MinIO locally)
S3_BUCKET=autonoma-local
S3_REGION=us-east-1
S3_ACCESS_KEY_ID=minioadmin
S3_SECRET_ACCESS_KEY=minioadmin

Everything else has sensible defaults or is optional for local development. The sections below cover every variable in detail.

How Environment Variables Work in This Project

Every app and package defines its environment variables in a dedicated env.ts file using createEnv from @t3-oss/env-core. This gives you:

  • Zod validation at startup - the process crashes immediately if a required variable is missing or malformed, rather than failing mysteriously at runtime.
  • Type safety - env.DATABASE_URL is typed as string, not string | undefined. No more process.env.DATABASE_URL! casts.
  • Composability - packages export their env object, and apps extend them. For example, the API server’s env.ts extends the database, storage, logger, and billing envs, inheriting all their variables.

You should never read process.env directly in application code. Always import from the nearest env.ts:

// Good
import { env } from "./env";
const port = env.API_PORT;
// Bad - bypasses validation
const port = process.env.API_PORT;

The emptyStringAsUndefined: true option is enabled everywhere, so setting a variable to an empty string is treated the same as not setting it at all.

For boolean variables, the codebase uses z.stringbool() which accepts "true", "false", "1", "0", "yes", and "no".


Core API Server

Source: apps/api/src/env.ts

The API server extends the database, storage, logger, and billing environments, so all variables from those sections apply here too.

VariableRequiredDefaultDescription
API_PORTYes-Port the API server listens on. Typically 4000.
INTERNAL_DOMAINNoautonoma.appInternal domain used for routing and service discovery.
ALLOWED_ORIGINSNohttp://localhost:3000Comma-separated list of CORS origins. Must include the frontend URL.
SCENARIO_ENCRYPTION_KEYYes-Key used to encrypt scenario data. Any non-empty string works for local dev.
GOOGLE_CLIENT_IDYes-OAuth 2.0 client ID from Google Cloud Console. Required for user authentication.
GOOGLE_CLIENT_SECRETYes-OAuth 2.0 client secret from Google Cloud Console.
AGENT_VERSIONNolatestVersion tag for the execution agent. Used when dispatching engine jobs.
POSTHOG_KEYNo-PostHog project API key for server-side analytics. Omit to disable analytics.
POSTHOG_HOSTNohttps://us.i.posthog.comPostHog ingestion endpoint. Override for self-hosted PostHog instances.
GEMINI_API_KEYYes-Google Gemini API key. Used by the API for AI features like test generation.
REDIS_URLYes-Redis connection string (e.g., redis://localhost:6379). Used for device locking, caching, and pub/sub.
TESTINGNofalseSet to true in test environments. Prevents importing certain modules. Not for general use.
ENGINE_BILLING_SECRETNo-Shared secret for authenticating billing calls from the engine.

Frontend (UI)

Source: apps/ui/src/env.ts

The frontend uses Vite’s import.meta.env and requires the VITE_ prefix for all variables.

VariableRequiredDefaultDescription
VITE_API_URLNohttp://localhost:4000URL of the API server. The frontend makes all tRPC calls to this address.
VITE_INTERNAL_DOMAINNoautonoma.appInternal domain, used for UI routing logic.
VITE_TEMPORAL_URLNo-URL of the Temporal UI. When set, enables links to workflow runs in the dashboard.
VITE_SENTRY_DSNNo-Sentry DSN for frontend error tracking. Omit to disable Sentry in the browser.
VITE_SENTRY_URLNo-Sentry organization URL. Used for linking to Sentry issues from the UI.
VITE_POSTHOG_KEYNo-PostHog project API key for frontend analytics. Omit to disable analytics. PostHog events are proxied through the API server at /ingest to bypass ad blockers.

Database

Source: packages/db/src/env.ts

VariableRequiredDefaultDescription
DATABASE_URLYes-PostgreSQL connection string. Format: postgresql://user:password@host:port/database. Used by Prisma for all database operations.

AI Services

Source: packages/ai/src/env.ts

These keys are required by the execution engines (web and mobile) and any service that runs AI inference. The API server only needs GEMINI_API_KEY directly - the other keys are consumed by the engine apps.

VariableRequiredDefaultDescription
GEMINI_API_KEYYes-Google Gemini API key. Used for the primary model (Gemini 3 Flash/Pro), point detection, object detection, and visual condition checking.
GROQ_KEYYes-Groq API key. Used for fast inference with open-source models (e.g., GPT-OSS-120B).
OPENROUTER_API_KEYYes-OpenRouter API key. Provides access to Ministral-8B and serves as a fallback provider for open-source models.

Storage (S3)

Source: packages/storage/src/env.ts

Used for storing screenshots, video recordings, test artifacts, and other binary assets.

VariableRequiredDefaultDescription
S3_BUCKETYes-S3 bucket name for storing artifacts.
S3_REGIONYes-AWS region of the S3 bucket (e.g., us-east-1).
S3_ACCESS_KEY_IDYes-AWS access key ID (or MinIO equivalent) for S3 authentication.
S3_SECRET_ACCESS_KEYYes-AWS secret access key (or MinIO equivalent) for S3 authentication.

Logging and Observability

Source: packages/logger/src/env.ts

VariableRequiredDefaultDescription
NODE_ENVNodevelopmentNode environment. Accepts development, production, or test. Affects log formatting and behavior.
SENTRY_DSNNo-Sentry DSN for backend error tracking and performance monitoring. Omit to disable Sentry.
SENTRY_ENVNoproductionSentry environment tag (e.g., staging, production).
SENTRY_RELEASENounknownSentry release identifier. Typically set to the git SHA or version tag in CI.
DEBUGNo-Debug filter string. When set, enables verbose debug logging for matching namespaces (e.g., autonoma:*).

Billing (Stripe)

Source: packages/billing/src/env.ts

Billing is entirely optional. When STRIPE_ENABLED is false (the default), all billing features are disabled and no other Stripe variables are needed.

VariableRequiredDefaultDescription
STRIPE_ENABLEDNofalseMaster switch for billing. Set to true to enable Stripe integration.
STRIPE_SECRET_KEYNo-Stripe secret API key. Required when STRIPE_ENABLED is true.
STRIPE_WEBHOOK_SECRETNo-Stripe webhook signing secret for verifying incoming webhook events. Required when STRIPE_ENABLED is true.
STRIPE_SUBSCRIPTION_PRICE_IDNo-Stripe Price ID for the subscription plan. Required when STRIPE_ENABLED is true.
STRIPE_TOPUP_PRICE_IDNo-Stripe Price ID for credit top-up purchases. Required when STRIPE_ENABLED is true.
BILLING_GRACE_PERIOD_DAYSNo3Number of days after a subscription lapses before access is revoked.
APP_URLNohttp://localhost:3000Frontend application URL. Used in Stripe checkout redirect URLs and billing emails.

Kubernetes and Workflows

Source: packages/k8s/src/env.ts and packages/workflow/src/env.ts

These variables are only needed in production or when running engine jobs on Kubernetes. Not required for local development.

VariableRequiredDefaultDescription
NAMESPACEYes (in K8s)-Kubernetes namespace where jobs are deployed. Used by @autonoma/k8s.

The workflow package also reads:

VariableRequiredDefaultDescription
DATABASE_URLYes-PostgreSQL connection string. The workflow package needs direct DB access for job coordination.
SENTRY_ENVNo-Sentry environment tag for workflow jobs.

Engine - Web (Playwright)

Source: apps/engine-web/src/platform/env.ts and apps/engine-web/src/execution-agent/env.ts

The web engine extends the AI, database, logger, and storage environments. All variables from those sections apply.

VariableRequiredDefaultDescription
REMOTE_BROWSER_URLNo-WebSocket URL of a remote browser instance (e.g., Browserless or Playwright remote). When omitted, launches a local Chromium browser.
HEADLESSNo-Set to any value to run Playwright in headless mode. When omitted, the browser window is visible (useful for local debugging).

Engine - Mobile (Appium)

Source: apps/engine-mobile/src/platform/env.ts

The mobile engine extends the AI, database, logger, and storage environments. All variables from those sections apply.

VariableRequiredDefaultDescription
APPIUM_HOSTNo-Hostname of the Appium server.
APPIUM_PORTNo-Port of the Appium server.
APPIUM_MJPEG_PORTNo-Port for the Appium MJPEG video stream. Used for live frame capture during test execution.
APPIUM_SYSTEM_PORTNo-System port used by Appium’s UiAutomator2 (Android) or WebDriverAgent (iOS).
APPIUM_SKIP_INSTALLATIONNotrueWhen true, skips reinstalling the app before each test. Speeds up repeated runs on the same device.
DEVICE_NAMENo-Name of the target device or emulator (e.g., iPhone 15 Pro, Pixel 7).
IOS_PLATFORM_VERSIONNo-iOS version to target (e.g., 17.2). Required for iOS testing.
ANDROID_DAEMON_HOSTSNo-Comma-separated list of Android daemon host addresses for distributed device access.
IOS_DAEMON_HOSTSNo-Comma-separated list of iOS daemon host addresses for distributed device access.
SKIP_DEVICE_DATE_UPDATENofalseWhen true, skips updating the device date/time before tests. Useful when the device clock is already correct.

Jobs

Execution Agent Runner

Source: packages/engine/src/execution-agent/runner/env.ts

VariableRequiredDefaultDescription
ARTIFACT_DIRNo-Local directory for saving test artifacts (screenshots, videos, step logs). Used by the local runner during development.

Run Completion Notification

Source: apps/jobs/run-completion-notification/src/env.ts

VariableRequiredDefaultDescription
DATABASE_URLYes-PostgreSQL connection string.
API_URLNo-API server URL for callbacks.
ENGINE_BILLING_SECRETNo-Shared secret for authenticating billing-related calls.
STRIPE_ENABLEDNofalseWhether to process billing events on run completion.

Diffs

Source: apps/jobs/diffs/src/env.ts

VariableRequiredDefaultDescription
BRANCH_IDYes-Branch identifier for computing diffs.
GEMINI_API_KEYYes-Gemini API key for AI-powered diff analysis.
GITHUB_APP_IDYes-GitHub App ID for repository access.
GITHUB_APP_PRIVATE_KEYYes-GitHub App private key (PEM format).
GITHUB_APP_WEBHOOK_SECRETYes-GitHub App webhook secret for verifying events.
AGENT_VERSIONNolatestVersion tag for the diff agent.

Generation Assigner

Source: apps/jobs/generation-assigner/src/env.ts

VariableRequiredDefaultDescription
AUTO_ACTIVATENo-When set, automatically activates generated test cases without manual review.

Review Jobs (Generation Reviewer, Replay Reviewer)

Source: packages/review/src/env.ts

Both the generation reviewer and replay reviewer jobs re-export from @autonoma/review/env, which extends the AI, logger, and storage environments. No additional variables beyond those from the AI, logger, and storage sections.


GitHub App

These variables appear in .env.example and are used by the API server and the diffs job for GitHub integration features (repository connections, PR-triggered test runs).

VariableRequiredDefaultDescription
GITHUB_APP_IDNo-GitHub App ID. Required for GitHub integration features.
GITHUB_APP_PRIVATE_KEYNo-GitHub App private key in PEM format.
GITHUB_APP_WEBHOOK_SECRETNo-Secret for verifying GitHub webhook payloads.
GITHUB_APP_SLUGNo-GitHub App slug (URL-friendly name). Used for generating installation links.

Authentication

These variables are referenced in .env.example for the Better Auth integration used by the API server.

VariableRequiredDefaultDescription
BETTER_AUTH_SECRETYes-Secret key for Better Auth session signing. Generate with openssl rand -hex 32.
BETTER_AUTH_URLYes-Base URL of the API server (e.g., http://localhost:4000). Used by Better Auth for callback URLs.

Tips for Local Development

What you can skip entirely:

  • Billing - Leave STRIPE_ENABLED=false (the default). No Stripe keys needed.
  • Analytics - Omit POSTHOG_KEY and VITE_POSTHOG_KEY. Analytics calls become no-ops.
  • Sentry - Omit SENTRY_DSN and VITE_SENTRY_DSN. Error tracking is disabled gracefully.
  • Kubernetes - Omit NAMESPACE. Only needed when deploying to K8s.
  • GitHub App - Omit all GITHUB_APP_* variables unless you are working on GitHub integration.
  • Temporal - Omit VITE_TEMPORAL_URL. The UI hides workflow links when this is unset.

What uses defaults that just work:

  • ALLOWED_ORIGINS defaults to http://localhost:3000 - correct for local dev.
  • VITE_API_URL defaults to http://localhost:4000 - correct for local dev.
  • APP_URL defaults to http://localhost:3000 - correct for local dev.
  • NODE_ENV defaults to development.
  • AGENT_VERSION defaults to latest.

What you must provide:

  • DATABASE_URL - there is no default. You need a running PostgreSQL instance.
  • REDIS_URL - there is no default. You need a running Redis instance.
  • GOOGLE_CLIENT_ID and GOOGLE_CLIENT_SECRET - required for authentication. Create OAuth credentials in the Google Cloud Console.
  • SCENARIO_ENCRYPTION_KEY - any non-empty string works locally.
  • BETTER_AUTH_SECRET - generate one with openssl rand -hex 32.
  • BETTER_AUTH_URL - set to http://localhost:4000.
  • AI keys (GEMINI_API_KEY, GROQ_KEY, OPENROUTER_API_KEY) - required if you are running test execution. Not needed if you are only working on the UI or API without triggering test runs.
  • S3 credentials - required for artifact storage. Use MinIO locally.
Link copied