Documentation Index
Fetch the complete documentation index at: https://docs.tesslate.com/llms.txt
Use this file to discover all available pages before exploring further.

Overview
All OpenSail configuration is environment-driven. The canonical reader isorchestrator/app/config.py (Pydantic settings). Feature flags live in orchestrator/app/config_features.py. Frontend runtime config reads window._env_.*; build-time config reads VITE_*.
Use this page together with:
- Repo-root
.env.exampleand.env.prod.example docs/guides/environment-variables.md(the exhaustive reference)- Kustomize overlays under
k8s/overlays/*/backend-patch.yaml
After changing a variable, restart the affected service. In Docker:
docker compose restart orchestrator. In Kubernetes: kubectl rollout restart deploy/orchestrator -n tesslate.Required core
JWT signing and general crypto fallback. Never reuse across environments. Generate with
python3 -c "import secrets; print(secrets.token_urlsafe(32))".docker, kubernetes, or desktop. Selects orchestrator backend, DB driver, task queue, and pub/sub.SQLAlchemy async URL. Docker default points at the
postgres service. Desktop mode resolves to SQLite automatically.Shared secret for cluster-internal callers (Volume Hub GC, btrfs CSI) hitting
/api/internal/*. Desktop mode ignores.Database
- Postgres (cloud)
- SQLite (desktop)
| Variable | Purpose |
|---|---|
POSTGRES_DB | Database name |
POSTGRES_USER | DB user |
POSTGRES_PASSWORD | DB password |
POSTGRES_PORT | Host port (compose default 5432) |
Redis, pub/sub, task queue
| Variable | Purpose |
|---|---|
REDIS_URL | ARQ + RedisPubSub connection. Empty string falls back to in-memory for single-process dev. |
WORKER_MAX_JOBS | Concurrent agent tasks per ARQ worker pod (default 10) |
WORKER_JOB_TIMEOUT | Task timeout seconds (default 600) |
LocalTaskQueue (asyncio + apscheduler) and LocalPubSub (in-process). No Redis required.
LiteLLM and agent
| Variable | Purpose |
|---|---|
LITELLM_API_BASE | Proxy URL, e.g. https://your-litellm.example.com/v1 |
LITELLM_MASTER_KEY | Master key for minting per-user virtual keys |
LITELLM_DEFAULT_MODELS | Comma-separated models granted to new users |
LITELLM_TEAM_ID | LiteLLM team or access group |
LITELLM_EMAIL_DOMAIN | Internal email domain stamped into LiteLLM users |
LITELLM_INITIAL_BUDGET | Starting budget USD per user |
COMPACTION_SUMMARY_MODEL | Cheap model used for context compaction |
DEFAULT_THINKING_EFFORT | Extended thinking effort for supported models |
AGENT_MAX_COST | Global cost cap USD (default 20.0) |
AGENT_MAX_ITERATIONS | Global iteration cap, 0 disables |
AGENT_MAX_COST_PER_RUN | Per-run cost cap USD (default 5.0) |
Auth and cookies
JWT signing algorithm.
Access token TTL.
Refresh token TTL.
Separate key for CSRF tokens. Falls back to
SECRET_KEY.CSRF token TTL seconds.
Set true in production.
lax, strict, or none.Scope cookies to apex, e.g.
.tesslate.com, for subdomain access.Comma-separated allowed origins.
Host header allowlist.
OAuth providers
All optional. Absence of credentials disables the provider gracefully.- Login
- Deployment targets
- MCP platform apps
| Provider | Variables |
|---|---|
| GitHub | GITHUB_CLIENT_ID, GITHUB_CLIENT_SECRET, GITHUB_OAUTH_REDIRECT_URI |
GOOGLE_CLIENT_ID, GOOGLE_CLIENT_SECRET, GOOGLE_OAUTH_REDIRECT_URI |
SMTP and 2FA
| Variable | Purpose |
|---|---|
SMTP_HOST, SMTP_PORT, SMTP_USERNAME, SMTP_PASSWORD, SMTP_USE_TLS, SMTP_SENDER_EMAIL | Email transport for magic links, 2FA codes, and password resets |
TWO_FA_ENABLED | Require 6-digit email 2FA after password login (default false) |
S3 and object storage
| Variable | Purpose |
|---|---|
S3_ACCESS_KEY_ID, S3_SECRET_ACCESS_KEY | Credentials. Omit on AWS with IRSA. |
S3_ENDPOINT_URL | Custom endpoint for DO Spaces, MinIO, etc. Omit for AWS S3. |
S3_BUCKET_NAME | Projects bucket (default tesslate-projects) |
S3_REGION | Region (default us-east-1) |
S3_PROJECTS_PREFIX | Key prefix (default projects) |
Kubernetes (user-project runtime)
| Variable | Purpose |
|---|---|
K8S_DEVSERVER_IMAGE | Image for user containers. Minikube uses tesslate-devserver:latest; prod uses an ECR URL. |
K8S_IMAGE_PULL_SECRET | Registry pull secret (ecr-credentials in prod) |
K8S_STORAGE_CLASS | StorageClass for PVCs |
K8S_SNAPSHOT_CLASS | VolumeSnapshotClass |
K8S_SNAPSHOT_RETENTION_DAYS | Days to keep soft-deleted snapshots (default 30) |
K8S_MAX_SNAPSHOTS_PER_PROJECT | Max snapshots in timeline (default 5) |
K8S_SNAPSHOT_READY_TIMEOUT_SECONDS | Snapshot readiness timeout (default 300) |
K8S_HIBERNATION_IDLE_MINUTES | Auto-hibernate after N idle minutes (default 10) |
K8S_HYDRATION_TIMEOUT_SECONDS, K8S_DEHYDRATION_TIMEOUT_SECONDS | Hibernation transitions |
K8S_PVC_SIZE | Default PVC size per project (default 5Gi) |
K8S_ENABLE_POD_AFFINITY | Keep multi-container projects on the same node |
K8S_RWX_STORAGE_CLASS | ReadWriteMany class for shared source code |
K8S_INGRESS_CLASS | Ingress class name (default nginx) |
K8S_NAMESPACE_PER_PROJECT | Namespace-per-project isolation (default true) |
K8S_ENABLE_NETWORK_POLICIES | Create NetworkPolicies for project isolation (default true) |
K8S_WILDCARD_TLS_SECRET | TLS secret for wildcard cert (empty for HTTP) |
K8S_INGRESS_DOMAIN | Apex domain for user-project ingress |
K8S_USE_S3_STORAGE | Use S3 hibernation instead of PVCs (default false) |
Volume Hub and btrfs CSI
| Variable | Purpose |
|---|---|
VOLUME_HUB_ADDRESS | Hub gRPC endpoint (default tesslate-volume-hub.kube-system.svc:9750) |
TEMPLATE_BUILD_STORAGE_CLASS | StorageClass for template builds (tesslate-btrfs) |
TEMPLATE_BUILD_NODEOPS_ADDRESS | NodeOps gRPC endpoint for template builds |
FILEOPS_ENABLED | Use FileOps gRPC service for v2 file operations (default true) |
FILEOPS_TIMEOUT | FileOps RPC timeout seconds (default 30) |
COMPUTE_MAX_CONCURRENT_PODS | Max concurrent compute pods (default 5) |
COMPUTE_POD_TIMEOUT | Pod readiness timeout (default 600) |
COMPUTE_REAPER_INTERVAL_SECONDS | Orphan pod reaper interval (default 60) |
COMPUTE_REAPER_MAX_AGE_SECONDS | Max pod age before reaping (default 900) |
Web search
| Variable | Purpose |
|---|---|
WEB_SEARCH_PROVIDER | tavily, brave, or duckduckgo (default tavily) |
TAVILY_API_KEY | Tavily API key |
BRAVE_SEARCH_API_KEY | Brave API key |
Messaging channels and gateway
| Variable | Purpose |
|---|---|
AGENT_DISCORD_WEBHOOK_URL | Webhook for the agent send_message tool |
CHANNEL_ENCRYPTION_KEY | Fernet key for encrypting per-user channel credentials |
GATEWAY_ENABLED | Enable gateway runner (default false) |
GATEWAY_SHARD | Shard identifier for multi-instance gateway |
GATEWAY_TICK_INTERVAL | Scheduler tick interval seconds |
GATEWAY_SESSION_IDLE_MINUTES | Idle timeout for gateway sessions |
GATEWAY_VOICE_TRANSCRIPTION | Enable voice message transcription |
MCP (Model Context Protocol)
| Variable | Purpose |
|---|---|
MCP_TOOL_CACHE_TTL | Tool schema cache TTL seconds (default 300) |
MCP_TOOL_TIMEOUT | Tool call timeout seconds (default 30) |
MCP_MAX_SERVERS_PER_USER | Cap on installed MCP servers per user (default 20) |
Stripe and billing
| Variable | Purpose |
|---|---|
STRIPE_SECRET_KEY, STRIPE_PUBLISHABLE_KEY, STRIPE_WEBHOOK_SECRET | Stripe core keys |
STRIPE_CONNECT_CLIENT_ID | Stripe Connect (creator payouts) |
STRIPE_BASIC_PRICE_ID, STRIPE_PRO_PRICE_ID, STRIPE_ULTRA_PRICE_ID | Monthly subscription prices |
STRIPE_BASIC_ANNUAL_PRICE_ID, STRIPE_PRO_ANNUAL_PRICE_ID, STRIPE_ULTRA_ANNUAL_PRICE_ID | Annual prices |
CREDIT_PACKAGE_SMALL, CREDIT_PACKAGE_MEDIUM, CREDIT_PACKAGE_LARGE, CREDIT_PACKAGE_TEAM | One-time credit prices (cents) |
SIGNUP_BONUS_CREDITS, SIGNUP_BONUS_EXPIRY_DAYS | Signup bonus |
CREATOR_REVENUE_SHARE, PLATFORM_REVENUE_SHARE | Revenue split decimals (sum to 1) |
USAGE_INVOICE_DAY | Day of month to generate usage invoices (1..28) |
Frontend
| Variable | Mode | Purpose |
|---|---|---|
VITE_API_URL | build | API base URL (empty for Vite proxy, or http://localhost:8000) |
VITE_ALLOWED_HOSTS | build | Comma-separated host allowlist for Vite dev server |
VITE_PUBLIC_POSTHOG_KEY, VITE_PUBLIC_POSTHOG_HOST | build | PostHog project |
window._env_.API_URL | runtime | Base URL without /api (frontend code prepends it) |
window._env_.POSTHOG_KEY, window._env_.POSTHOG_HOST | runtime | PostHog runtime config |
Domain, ports, Traefik
| Variable | Purpose |
|---|---|
APP_DOMAIN | Apex domain (no protocol) |
APP_PROTOCOL | http or https |
APP_PORT, APP_SECURE_PORT | Public HTTP and HTTPS ports |
BACKEND_PORT | Uvicorn port |
FRONTEND_PORT | Vite dev port |
APP_BASE_URL | Full base URL; defaults to protocol + domain |
TRAEFIK_DASHBOARD_PORT | Dashboard port (dev) |
TRAEFIK_BASIC_AUTH | htpasswd admin credential |
TRAEFIK_CERT_RESOLVER | letsencrypt or cloudflare |
CF_DNS_API_TOKEN | Cloudflare DNS token for wildcard certs |
Desktop
| Variable | Purpose |
|---|---|
OPENSAIL_HOME | Desktop data directory override. Resolved by orchestrator/app/services/desktop_paths.py. |
TEST_HELPERS_ENABLED | Expose test-only routes (CI) |
BUILD_SHA | Deployment identifier reported by /api/version |
Observability
| Variable | Purpose |
|---|---|
LOG_LEVEL | DEBUG, INFO, WARNING, ERROR, CRITICAL (default INFO) |
VITE_PUBLIC_POSTHOG_KEY | PostHog project key (empty to disable) |
Feature flags (Tesslate Apps)
Apps features are gated byTSL_FEATURE_* booleans. Default is off except governance policies. The env variable is the dotted flag name upper-cased with dots replaced by underscores: apps.publish becomes TSL_FEATURE_APPS_PUBLISH.
| Flag | Default |
|---|---|
apps.manifest_schema_v1, apps.publish, apps.install | false |
apps.runtime.ui, apps.runtime.chat, apps.runtime.scheduled, apps.runtime.triggered, apps.runtime.mcp_tool | false |
apps.hosted_agent, apps.source_view, apps.fork, apps.bundles | false |
apps.review.stage1, apps.review.stage2, apps.review.stage3, apps.yank | false |
apps.yank.critical_two_admin | true (governance policy) |
apps.billing.dispatcher, apps.billing.revenue_split | false |
apps.triggers.webhook, apps.triggers.mcp_event, apps.triggers.app_invocation | false |
apps.canvas.hosted_agent_node, apps.embedding.postmessage | false |
Testing
| Variable | Purpose |
|---|---|
TEST_HELPERS_ENABLED | Expose test-only routes in CI |
PLAYWRIGHT_BASE_URL | Base URL for Playwright E2E |
SECRET_KEY=test-secret-key-*, DEPLOYMENT_MODE=docker, LITELLM_API_BASE=http://localhost:4000/v1, LITELLM_MASTER_KEY=test-key, and points DATABASE_URL at Postgres on port 5433.
Environment comparison
| Setting | Docker (Local) | Minikube | AWS EKS |
|---|---|---|---|
DEPLOYMENT_MODE | docker | kubernetes | kubernetes |
K8S_DEVSERVER_IMAGE | N/A | tesslate-devserver:latest | <ECR_URL>/tesslate-devserver:latest |
K8S_IMAGE_PULL_SECRET | N/A | (empty) | ecr-credentials |
K8S_STORAGE_CLASS | N/A | tesslate-btrfs | tesslate-block-storage |
K8S_WILDCARD_TLS_SECRET | N/A | (empty, HTTP) | tesslate-wildcard-tls |
APP_DOMAIN | localhost | localhost | e.g. opensail.example.com |
COOKIE_SECURE | false | false | true |
Next steps
Deployment
Production paths: Docker, Kubernetes, AWS EKS.
Architecture
How the orchestrator, agent, and storage fit together.
Authentication
JWT, OAuth, email 2FA, API keys, and desktop pairing.
API reference
REST surface overview and OpenAPI spec pointer.