-
Notifications
You must be signed in to change notification settings - Fork 687
Expand file tree
/
Copy path.env.example
More file actions
589 lines (509 loc) · 31.5 KB
/
Copy path.env.example
File metadata and controls
589 lines (509 loc) · 31.5 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
# ODS Configuration
# Copy this file to .env and edit values before starting:
# cp .env.example .env
#
# The installer (install-core.sh) generates .env automatically with
# secure random secrets. This file documents all available variables.
# ODS version (auto-set by installer, used by ods-cli for compat checks)
# ODS_VERSION=2.6.0
# LiteLLM proxy API key for internal service auth
# TARGET_API_KEY=not-needed
# ═══════════════════════════════════════════════════════════════════
# REQUIRED — these must be set or docker compose will refuse to start
# ═══════════════════════════════════════════════════════════════════
# Session signing for Open WebUI (generate: openssl rand -hex 32)
WEBUI_SECRET=CHANGEME
# n8n workflow automation credentials
N8N_USER=admin@ods.local
N8N_PASS=CHANGEME
# LiteLLM API gateway key (generate: echo "sk-ods-$(openssl rand -hex 16)")
LITELLM_KEY=CHANGEME
# LiveKit real-time communication credentials
LIVEKIT_API_KEY=CHANGEME
LIVEKIT_API_SECRET=CHANGEME
# Dify agent platform secret key
DIFY_SECRET_KEY=CHANGEME
# SearXNG session secret (generate: openssl rand -hex 32)
SEARXNG_SECRET=CHANGEME
# OpenCode web UI password (generate: openssl rand -base64 16)
OPENCODE_SERVER_PASSWORD=CHANGEME
# OpenClaw gateway token (generate: openssl rand -hex 24)
OPENCLAW_TOKEN=CHANGEME
# ═══════════════════════════════════════════════════════════════════
# OpenClaw Security
# ═══════════════════════════════════════════════════════════════════
#
# OpenClaw device authentication (device pairing) defaults to ON. Token auth
# and device auth are separate gates: a valid OPENCLAW_TOKEN still auto-
# connects the local Control UI with device auth enabled, so you normally do
# NOT need to change this.
#
# Setting this to "true" DISABLES device pairing entirely. Anyone who can
# reach the gateway then gets an UNAUTHENTICATED agent with exec / read /
# write tools — especially dangerous with a widened BIND_ADDRESS
# (LAN / Tailscale / 0.0.0.0). Only enable as a deliberate, understood
# escape hatch; a loud warning banner is logged at startup when set.
# Leave unset (the secure default) unless you fully accept the risk.
# OPENCLAW_DANGEROUSLY_DISABLE_DEVICE_AUTH=
# OPENCLAW_LLM_URL=
# OPENCLAW_HTTP_API=
# ═══════════════════════════════════════════════════════════════════
# Network Binding
# ═══════════════════════════════════════════════════════════════════
# Bind address for all Docker port bindings.
# 127.0.0.1 = localhost only (secure default)
# 0.0.0.0 = accessible from LAN (headless servers, see SECURITY.md)
# BIND_ADDRESS=127.0.0.1
# ═══════════════════════════════════════════════════════════════════
# LLM Backend Mode
# ═══════════════════════════════════════════════════════════════════
# local = llama-server (default, requires GPU or CPU inference)
# cloud = LiteLLM -> cloud APIs (no local GPU needed)
# hybrid = local primary, cloud fallback
ODS_MODE=local
# Model Switchboard rollout: legacy / observe / enabled.
# enabled routes supported apps through the stable ods/current alias.
ODS_MODEL_SWITCHBOARD=observe
# Inference backend engine: llama-server (NVIDIA/CPU), lemonade (AMD),
# litellm (cloud), or external (installer-validated Ollama/LM Studio)
# AMD hardware auto-selects lemonade for NPU/Vulkan/ROCm acceleration
LLM_BACKEND=llama-server
# API base path: /v1 for llama-server, /api/v1 for Lemonade (set by installer)
LLM_API_BASE_PATH=/v1
LLM_API_URL=http://llama-server:8080
# Enabled switchboard installs set these so Open WebUI talks to LiteLLM/ods-current.
OPEN_WEBUI_LLM_BASE_URL=
OPEN_WEBUI_LLM_API_KEY=
# LLM_URL= # Optional dashboard-api diagnostics override; normally follows LLM_API_URL
# Reuse a host-managed Ollama or LM Studio model instead of downloading and
# starting ODS's llama-server. Configure this through install.sh so the
# endpoint/model are validated and the Compose topology is updated atomically:
# ./install.sh --external-llm-url http://127.0.0.1:11434 \
# --external-llm-provider ollama --external-llm-model qwen3.5:9b
# Interactive installs can discover a matching model and ask before reuse.
# Non-interactive discovery is opt-in with --reuse-external-llm.
# Use ./install.sh --no-external-llm to return a persisted install to managed
# local inference. EXTERNAL_LLM_URL is host-facing; the installer derives the
# container-facing host.docker.internal URL.
EXTERNAL_LLM_URL=
EXTERNAL_LLM_CONTAINER_URL=
EXTERNAL_LLM_PROVIDER=
EXTERNAL_LLM_MODEL=
SKIP_MODEL_DOWNLOAD=false
# Remote GPU provider metadata. Remote routing is active only when
# ODS_MODE=cloud and REMOTE_LLM_ENABLED=true. Provider API keys, peer tokens,
# SSH identities, and CA material are write-only lifecycle inputs; do not put
# them in .env.
REMOTE_LLM_ENABLED=false
REMOTE_LLM_TRANSPORT=
REMOTE_LLM_BASE_URL=
REMOTE_LLM_MODEL=
REMOTE_LLM_TLS_CA_FILE=
REMOTE_LLM_SSH_HOST=
REMOTE_LLM_SSH_USER=
REMOTE_LLM_SSH_PORT=
REMOTE_LLM_SSH_INFERENCE_HOST=
REMOTE_LLM_SSH_INFERENCE_PORT=
REMOTE_LLM_SSH_CONTROL_HOST=
REMOTE_LLM_SSH_CONTROL_PORT=
REMOTE_ODS_PEER_URL=
# ODS Talk image attachment vision backend. Leave empty to use the local
# inference backend. May be a host root (http://host:8080) or an
# OpenAI-compatible base URL (http://host:8080/v1 or /api/v1).
ODS_TALK_VISION_URL=
ODS_TALK_VISION_KEY=
ODS_TALK_VISION_MODEL=user.Qwen3.6-35B-A3B-Vision
# AMD local inference runtime selected by the installer.
# Linux AMD: lemonade / rocm / container
# Windows AMD: lemonade or llama-server / vulkan / host
AMD_INFERENCE_RUNTIME=
AMD_INFERENCE_BACKEND=
AMD_INFERENCE_LOCATION=
AMD_INFERENCE_PORT=8080
AMD_INFERENCE_SUPPORTED_BACKENDS=
AMD_INFERENCE_RUNTIME_MODE=
AMD_INFERENCE_MANAGED=
LEMONADE_EXTERNAL=false
LEMONADE_BASE_URL=
LEMONADE_CONTAINER_BASE_URL=
LEMONADE_API_BASE_PATH=/api/v1
LEMONADE_MODEL=
# ═══════════════════════════════════════════════════════════════════
# Provider and Hub Credentials
# ═══════════════════════════════════════════════════════════════════
ANTHROPIC_API_KEY=
OPENAI_API_KEY=
# Optional in every mode: read token for private/gated Hugging Face models.
HF_TOKEN=
# Comma-separated HTTPS hosts permitted for model artifact downloads.
# ODS_MODEL_DOWNLOAD_ALLOWED_HOSTS=huggingface.co,www.huggingface.co,hf.co
TOGETHER_API_KEY=
MINIMAX_API_KEY=
# ═══════════════════════════════════════════════════════════════════
# LLM Settings (llama-server)
# ═══════════════════════════════════════════════════════════════════
# Optional model family profile for installer-driven tier selection.
# qwen = keep the current stable ODS defaults
# gemma4 = always use Gemma 4 tier mappings when possible
# auto = prefer Gemma 4 on capable hardware, keep Qwen fallback for minimum/cloud paths
MODEL_PROFILE=qwen
# Model GGUF filename override (installer normally rewrites this from tier + MODEL_PROFILE)
GGUF_FILE=Qwen3.5-9B-Q4_K_M.gguf
# Context window size (tokens)
CTX_SIZE=16384
# GPU backend: nvidia or amd
GPU_BACKEND=nvidia
# Unified system RAM in GB (macOS Apple Silicon only — written by env-generator.sh).
# Passed to llama.cpp for the Metal backend to size the unified-memory pool.
# HOST_RAM_GB=24
# Model name override (installer normally rewrites this from tier + MODEL_PROFILE)
LLM_MODEL=qwen3.5-9b
# Installer recommendation metadata. During fast-start bootstrap, LLM_MODEL/GGUF_FILE
# may temporarily point at the small bootstrap model while these fields keep the
# full hardware-selected target visible in the dashboard.
MODEL_RECOMMENDED_MODEL=qwen3.5-9b
MODEL_RECOMMENDED_GGUF=Qwen3.5-9B-Q4_K_M.gguf
MODEL_RECOMMENDED_CONTEXT=16384
MODEL_RECOMMENDATION_SOURCE=catalog_fit_pre_download
MODEL_RECOMMENDATION_POLICY=context-aware-largest-capable-general-v1
MODEL_RECOMMENDATION_CONFIDENCE=high
MODEL_RECOMMENDATION_REASON=Catalog fit (context-aware-largest-capable-general-v1): Qwen 3.5 9B needs about 8GB including context/KV, fits 8.0GB GPU VRAM on nvidia, and gives 32K context. Throughput requires a local benchmark after first launch.
MODEL_RECOMMENDED_ALTERNATIVES=qwen3.5-9b-q4:32768:8;phi4-mini-q4:128000:4.38;deepseek-r1-7b-q4:32768:7
MODEL_PERFORMANCE_SOURCE=benchmark_required
MODEL_PERFORMANCE_LABEL=Benchmark after first launch
MODEL_RUNTIME_PROFILE=
MODEL_RUNTIME_PROFILE_LABEL=
MODEL_RUNTIME_PROFILE_SOURCE=
SYSTEM_RAM_GB=32
# Optional llama.cpp image override (installer sets this automatically for runtime profiles)
# LLAMA_SERVER_IMAGE=ghcr.io/ggml-org/llama.cpp:server-cuda-b9014
# Optional explicit fallback if a custom llama.cpp image tag disappears
# LLAMA_SERVER_IMAGE_FALLBACK=ghcr.io/ggml-org/llama.cpp:server-cuda-b9014
# Optional AMD Lemonade image override. Default is pinned in config/backends/amd.json.
# LEMONADE_SERVER_IMAGE=ghcr.io/lemonade-sdk/lemonade-server:v10.2.0
# ─── Architecture-specific overrides ────────────────────────────────────────────
# WHISPER_ACCELERATION is normally written by the installer. On Windows NVIDIA
# systems with drivers too old for the CUDA Whisper image, ODS keeps the rest of
# the GPU stack enabled and runs Whisper on CPU.
# WHISPER_ACCELERATION=cuda
# WHISPER_IMAGE is a forward-compat escape hatch. Windows fallback may set the
# CPU image when the CUDA tag cannot run on the installed driver.
# WHISPER_IMAGE=ghcr.io/speaches-ai/speaches:0.9.0-rc.3-cuda
# llama-server inference tuning (advanced)
# N_GPU_LAYERS=auto # auto | all | non-negative layer count
# LLAMA_BATCH_SIZE=2048 # Batch size for prompt processing (higher = faster prefill)
# LLAMA_THREADS=4 # CPU threads for non-GPU work
# LLAMA_PARALLEL=1 # Concurrent request slots (increase for multi-user)
# LLAMA_ARG_FLASH_ATTN=auto # auto | on | off. Use on for long-context CUDA/Metal/SYCL tuning.
# LLAMA_ARG_CACHE_TYPE_K=f16 # KV cache key type: f16 (default) or q8_0 for lower VRAM/RAM.
# LLAMA_ARG_CACHE_TYPE_V=f16 # KV cache value type: f16 (default) or q8_0 for lower VRAM/RAM.
# LLAMA_ARG_N_CPU_MOE=25 # Optional MoE only: keep first N MoE expert layers on CPU/RAM.
# LLAMA_ARG_NO_CACHE_PROMPT=1 # Optional profile flag for long-context MoE runs.
# LLAMA_ARG_CHECKPOINT_EVERY_N_TOKENS=-1 # Optional profile flag to disable context checkpoints.
# LLAMA_ARG_SPEC_TYPE=draft-mtp # Optional: only for MTP-capable GGUFs and llama.cpp builds.
# LLAMA_ARG_SPEC_DRAFT_N_MAX=3 # Optional: speculative draft cap; benchmark per model/runtime.
# LLAMA_CPU_LIMIT=12.0 # Auto-generated: capped to CPUs actually exposed by Docker
# LLAMA_CPU_RESERVATION=2.0 # Auto-generated: reservation capped to the same ceiling
# TTS_CPU_LIMIT=8.0 # Auto-generated: capped to Docker CPUs
# TTS_CPU_RESERVATION=2.0 # Auto-generated: capped to the TTS limit
# WHISPER_CPU_LIMIT=4.0 # Auto-generated: capped to Docker CPUs
# WHISPER_CPU_RESERVATION=1.0 # Auto-generated: capped to the Whisper limit
# HERMES_CPU_LIMIT=4.0 # Auto-generated: capped to Docker CPUs
# HERMES_CPU_RESERVATION=0.5 # Auto-generated: capped to the Hermes limit
# COMFYUI_CPU_LIMIT=16.0 # Auto-generated: capped to Docker CPUs
# COMFYUI_CPU_RESERVATION=2.0 # Auto-generated: capped to the ComfyUI limit
# LLAMA_START_PERIOD=240s # Healthcheck grace window for cold model load (bump for 70B-class on slow NVMe)
# ═══════════════════════════════════════════════════════════════════
# Ports — all overridable, defaults shown
# ═══════════════════════════════════════════════════════════════════
OLLAMA_PORT=11434 # llama-server API (external → internal 8080)
WEBUI_PORT=3000 # Open WebUI (external → internal 8080)
# SEARXNG_PORT=8888 # SearXNG metasearch (external → internal 8080)
# PERPLEXICA_PORT=3004 # Perplexica deep research (external → internal 3000)
# WHISPER_PORT=9000 # Whisper STT (external → internal 8000)
# TTS_PORT=8880 # Kokoro TTS (external → internal 8880)
# N8N_PORT=5678 # n8n workflows (external → internal 5678)
# QDRANT_PORT=6333 # Qdrant vector DB (external → internal 6333)
# QDRANT_GRPC_PORT=6334 # Qdrant gRPC (external → internal 6334)
# EMBEDDINGS_PORT=8090 # Text embeddings (external → internal 80)
# LITELLM_PORT=4000 # LiteLLM gateway (external → internal 4000)
# OPENCLAW_PORT=7860 # OpenClaw agent (external → internal 18789)
# SHIELD_PORT=8085 # Privacy Shield (external → internal 8085)
# DASHBOARD_API_PORT=3002 # Dashboard API (external → internal 3002)
# DASHBOARD_PORT=3001 # Dashboard UI (external → internal 3001)
# COMFYUI_PORT=8188 # ComfyUI image gen (external → internal 8188)
# TOKEN_SPY_PORT=3005 # Token Spy usage monitor (external → internal 8080)
# OPENCODE_PORT=3003 # OpenCode IDE web UI (host service)
# ═══════════════════════════════════════════════════════════════════
# Optional Security
# ═══════════════════════════════════════════════════════════════════
# Host Agent bind address (leave empty for platform-aware default).
# macOS/Windows: defaults to 127.0.0.1 (Docker Desktop routes via loopback).
# Linux: auto-detects Docker bridge gateway IP (e.g. 172.17.0.1) so containers
# can reach the agent while LAN devices cannot. Falls back to 127.0.0.1 if
# detection fails. Set explicitly to override.
# ODS_AGENT_BIND=
# Host Agent HTTP port used by dashboard-api for privileged host operations.
# ODS_AGENT_PORT=7710
# Hostname/IP dashboard-api containers use to reach ods-host-agent.
# Docker Desktop uses host.docker.internal; Colima installers set the private
# vmnet host gateway because its user-mode host route can become unreachable.
# ODS_AGENT_HOST=host.docker.internal
# Managed macOS/Colima private bridge state. Installers discover these values;
# do not set them manually unless repairing a custom Colima network profile.
# ODS_MACOS_HOST_GATEWAY=
# ODS_MACOS_VM_IP=
# ODS_MACOS_LLM_BRIDGE_ENABLED=
# ODS_MACOS_HOST_AGENT_BRIDGE_ENABLED=
# ODS_NATIVE_LLAMA_PORT=8080
# Dashboard API key (generate: openssl rand -hex 32)
# DASHBOARD_API_KEY=
# ODS host agent key (generate: openssl rand -hex 32) — auto-generated by installer; rotating breaks host-agent authentication
# ODS_AGENT_KEY=
# Session-cookie signing secret. Used by dashboard-api to mint
# HMAC-signed `ods-session` cookies at magic-link redemption, and
# by the Hermes auth-proxy to verify them via /api/auth/verify-session.
# Generate with: openssl rand -hex 32. Rotating invalidates all
# currently-issued session cookies (forces re-redemption).
# ODS_SESSION_SECRET=
# Internal Hermes dashboard/WebSocket token. Auto-generated by the installer
# and kept stable across container restarts. Rotating it requires clients with
# an open Hermes tab to refresh.
# HERMES_DASHBOARD_SESSION_TOKEN=
# Public/custom URL and cookie domain for invite links, tunnels, and
# subdomain SSO. Leave empty for normal localhost or mDNS LAN generation.
# ODS_PUBLIC_URL=
# Optional reverse-proxy browser URLs. The dashboard uses these exact URLs
# for service launch links before falling back to the current host + port.
# ODS_SERVICE_PUBLIC_URLS={"open-webui":"https://chat.example.com","comfyui":"https://comfy.example.com"}
# OPEN_WEBUI_PUBLIC_URL=https://chat.example.com
# COMFYUI_PUBLIC_URL=https://comfy.example.com
# N8N_PUBLIC_URL=https://n8n.example.com
# ODS_TALK_PUBLIC_URL=https://talk.example.com
# ODS_COOKIE_DOMAIN=
# Privacy Shield API key (generate: openssl rand -hex 32) - auto-generated by installer; shared between dashboard-api and privacy-shield containers
# SHIELD_API_KEY=
# Qdrant API key (generate: openssl rand -hex 32)
# QDRANT_API_KEY=
# Token Spy API key (auto-generated by installer; shared with dashboard-api)
# TOKEN_SPY_API_KEY=
# ═══════════════════════════════════════════════════════════════════
# Langfuse (LLM Observability) — optional, disabled by default
# ═══════════════════════════════════════════════════════════════════
LANGFUSE_PORT=3006
LANGFUSE_ENABLED=false
LANGFUSE_NEXTAUTH_SECRET= # auto-generated during install
LANGFUSE_SALT= # auto-generated during install
LANGFUSE_ENCRYPTION_KEY= # auto-generated during install
LANGFUSE_DB_PASSWORD= # auto-generated during install
LANGFUSE_CLICKHOUSE_PASSWORD= # auto-generated during install
LANGFUSE_REDIS_PASSWORD= # auto-generated during install
LANGFUSE_MINIO_ACCESS_KEY= # auto-generated during install
LANGFUSE_MINIO_SECRET_KEY= # auto-generated during install
LANGFUSE_PROJECT_PUBLIC_KEY= # auto-generated during install
LANGFUSE_PROJECT_SECRET_KEY= # auto-generated during install
LANGFUSE_INIT_PROJECT_ID= # auto-generated during install
LANGFUSE_INIT_USER_EMAIL=admin@ods.local
LANGFUSE_INIT_USER_PASSWORD= # auto-generated during install
# ═══════════════════════════════════════════════════════════════════
# Multi-GPU Settings (auto-populated by installer for multi-GPU)
# ═══════════════════════════════════════════════════════════════════
# GPU_ASSIGNMENT_JSON_B64= # Base64-encoded GPU assignment JSON
# LLAMA_SERVER_GPU_UUIDS= # GPU UUIDs for llama-server (NVIDIA, comma-separated)
# LLAMA_SERVER_GPU_INDICES= # GPU indices for llama-server (AMD, comma-separated)
# LLAMA_ARG_SPLIT_MODE=none # none | layer (pipeline) | row (tensor/hybrid)
# LLAMA_ARG_TENSOR_SPLIT= # Proportional VRAM weights (e.g. 3,1)
# COMFYUI_GPU_UUID= # GPU UUID for ComfyUI (NVIDIA)
# WHISPER_GPU_UUID= # GPU UUID for Whisper (NVIDIA)
# EMBEDDINGS_GPU_UUID= # GPU UUID for embeddings (NVIDIA)
# ROCR_VISIBLE_DEVICES= # AMD GPU indices visible to ROCm (comma-separated)
# VIDEO_GID=44 # Host 'video' group GID (AMD)
# RENDER_GID=992 # Host 'render' group GID (AMD)
# HSA_OVERRIDE_GFX_VERSION= # AMD gfx version override for ROCm compatibility
# LLM_MODEL_SIZE_MB= # Approximate model size in MB
# ═══════════════════════════════════════════════════════════════════
# Optional — Voice, Web UI, n8n
# ═══════════════════════════════════════════════════════════════════
# Whisper model (tiny, base, small, medium, large-v3-turbo)
# WHISPER_MODEL=base
# Open WebUI STT settings. Installer auto-selects AUDIO_STT_MODEL by GPU:
# NVIDIA → deepdml/faster-whisper-large-v3-turbo-ct2 (faster, ~1.5GB)
# AMD/CPU → Systran/faster-whisper-base (~130MB)
# Override to use a different model — must then run `ods restart` and
# manually download the new model via:
# curl -X POST --max-time 3600 http://localhost:9000/v1/models/<url-encoded-model-id>
# AUDIO_STT_ENGINE=openai
# AUDIO_STT_OPENAI_API_BASE_URL=http://whisper:8000/v1
# AUDIO_STT_OPENAI_API_KEY=
# WHISPER_ACCELERATION=cpu
# AUDIO_STT_MODEL=Systran/faster-whisper-base
# Internal URLs used by dashboard-api and ODS Talk when running diagnostics
# or voice flows from inside the Docker network.
# WHISPER_URL=http://whisper:8000
# TTS_URL=http://tts:8880
# EMBEDDING_URL=http://embeddings:80
# Kokoro/Open WebUI TTS settings
# AUDIO_TTS_ENGINE=openai
# AUDIO_TTS_OPENAI_API_BASE_URL=http://tts:8880/v1
# AUDIO_TTS_OPENAI_API_KEY=
# AUDIO_TTS_MODEL=kokoro
# AUDIO_TTS_VOICE=af_heart
# Legacy Kokoro TTS voice name
# TTS_VOICE=en_US-lessac-medium
# Open WebUI authentication (true/false). Installers default this to false for
# loopback-only ODS and true when services are exposed to the network.
# WEBUI_AUTH=false
# Open WebUI PWA / branding name. Shown as the app title, page title, and PWA
# install label (the text next to the icon on a phone's home screen).
# WEBUI_NAME=ODS
# Optional Open WebUI public URL — used for share links, OAuth callbacks, and
# PWA install metadata. Leave empty for traditional localhost usage. After
# enabling ods-proxy + mDNS, set this to the reachable chat subdomain:
# http://chat.<ODS_DEVICE_NAME>.local. Override with a Tailscale Funnel /
# Cloudflare Tunnel / custom domain URL when fronted by one.
# WEBUI_URL=http://chat.ods.local
# Device name used by mDNS announcements and as the hostname segment for
# proxy/headless URLs. Letters / digits / hyphens only — short and memorable
# wins (e.g. "ods", "kitchen", "lab").
# ODS_DEVICE_NAME=ods
# Web search settings
# ENABLE_WEB_SEARCH=true
# WEB_SEARCH_ENGINE=searxng
# System timezone (used by Open WebUI and n8n)
# TIMEZONE=UTC
# n8n settings
# N8N_HOST=localhost # n8n hostname
# N8N_WEBHOOK_URL=http://localhost:5678 # n8n webhook URL (for external access)
# N8N_SECURE_COOKIE=auto # false only for loopback HTTP; true for HTTPS/LAN
# N8N_PROXY_HOPS=0 # set to the proxy count when using HTTPS ingress
# Embedding model served by the bundled Hugging Face TEI runtime. Use a TEI-
# compatible Hugging Face repository ID; GGUF/Q4 files are not supported here.
# EMBEDDING_MODEL=BAAI/bge-base-en-v1.5
# Open WebUI uses EMBEDDING_MODEL as its first-boot default. After first boot,
# its Admin Panel value is persistent. Set this override only when the endpoint
# points to a different embeddings provider/model.
# RAG_EMBEDDING_MODEL=
# RAG_OPENAI_API_BASE_URL=http://embeddings:80/v1
# RAG_OPENAI_API_KEY= # only for authenticated external providers
# Larger models such as BAAI/bge-m3 may need a higher container memory limit.
# EMBEDDINGS_MEMORY_LIMIT=4G
# Image generation (ComfyUI + SDXL Lightning)
# ENABLE_IMAGE_GENERATION=true
# ═══════════════════════════════════════════════════════════════════
# Agent Policy Engine (APE)
# ═══════════════════════════════════════════════════════════════════
#
# APE audits and can enforce policy decisions for agent tool usage.
# APE_PORT=7890
# APE_RATE_LIMIT_RPM=60
# APE_STRICT_MODE=false
# ═══════════════════════════════════════════════════════════════════
# AMD-specific (only needed with GPU_BACKEND=amd)
# ═══════════════════════════════════════════════════════════════════
# VIDEO_GID=44 # `getent group video | cut -d: -f3`
# RENDER_GID=992 # `getent group render | cut -d: -f3`
# HSA_OVERRIDE_GFX_VERSION=11.5.1 # Required for Strix Halo gfx1151
# HSA_XNACK=1 # Extended memory access for large KV caches
# ROCBLAS_USE_HIPBLASLT=1 # 2-3x faster prompt processing via hipBLASLt
# AMDGPU_TARGET=gfx1151 # GPU arch for llama.cpp build (gfx1151, gfx1100, etc.)
# LLAMA_CPP_REF=b8763 # llama.cpp release tag to build (pin to avoid breakage)
# ═══════════════════════════════════════════════════════════════════
# Advanced
# ═══════════════════════════════════════════════════════════════════
# Container user/group IDs
# UID=1000
# GID=1000
# Privacy Shield settings
# PII_CACHE_ENABLED=true
# PII_CACHE_SIZE=1000
# PII_CACHE_TTL=300
# LOG_LEVEL=info
# OpenClaw bootstrap model (small model for instant startup)
# BOOTSTRAP_MODEL=qwen3:8b-q4_K_M
# Dashboard API internal URLs (usually Docker-internal, not user-facing)
# KOKORO_URL=http://tts:8880
# N8N_URL=http://n8n:5678
# NVIDIA llama-server memory limit (Docker). When unset, installers reserve
# memory for the host and other ODS services, cap the result at 64G, and use
# the smaller of physical RAM and Docker Desktop's VM allocation.
# Set an explicit value to override the calculated limit. Remove the generated
# key before rerunning the installer if Docker's memory allocation changes and
# you want ODS to calculate it again.
# LLAMA_SERVER_MEMORY_LIMIT=64G
# llama-server CPU core limit (auto-capped during install/update)
# Tune this to control how many CPU cores llama-server may use.
# LLAMA_CPU_LIMIT=8.0
# ═══════════════════════════════════════════════════════════════════
# ODS Proxy (LAN reverse proxy on port 80)
# ═══════════════════════════════════════════════════════════════════
# Opt-in Caddy reverse proxy that fronts dashboard / chat / API on
# port 80, so `http://<device>.local` (no port) works from any LAN
# device. Without this, services bind to 127.0.0.1 and `ods.local`
# resolves to a port that's not open.
# Enable: `ods enable ods-proxy`. See docs/ODS-PROXY.md.
#
# ODS_PROXY_PORT=80 # Host port (standard HTTP)
# ODS_PROXY_TLS_PORT=443 # HTTPS port (deferred; HTTP only in v1)
# ODS_PROXY_BIND=0.0.0.0 # LAN-exposed by default — that's the point
# Hermes Agent (Remote-capable Chat + Generalist Agent)
# ═══════════════════════════════════════════════════════════════════
# Hermes Agent (Nous Research, MIT) — chat-first generalist agent with
# persistent memory, autonomous skill creation, and 70+ tools. ODS
# Server runs the upstream image pinned by version and points it at the
# local LLM. Browser UI ships in the upstream image (port 9119).
# Enable: `ods enable hermes`. Owner-card users reach the mobile ODS
# Talk portal at http://talk.<device>.local/talk; advanced users can still
# reach Hermes at http://hermes.<device>.local (auth-gated by the proxy).
# Hermes itself is internal-only —
# there's no HERMES_PORT knob in this stack.
#
# HERMES_LLM_BASE_URL=http://llama-server:8080/v1 # OpenAI-compat endpoint
# HERMES_LLM_API_KEY=sk-ods-hermes-local # Dummy (OpenAI SDK requires non-empty)
# HERMES_AGENT_IMAGE=nousresearch/hermes-agent:v2026.6.5 # Upstream Hermes image
# HERMES_AGENT_IMAGE_FALLBACK= # Optional explicit fallback if upstream retags
# HERMES_LANGUAGE=en # UI language
# SEARXNG_URL=http://searxng:8080 # Hermes web-search backend
# (No HERMES_MODEL_NAME — the model lives in /opt/data/config.yaml,
# not in env. Edit the file after first start to switch models.)
#
# Optional Hermes WhatsApp gateway. Disabled by default; ODS's Hermes
# config pins WhatsApp's internal bridge to 3010 so it does not collide with
# Open WebUI's host port 3000 when users intentionally enable WhatsApp.
# WHATSAPP_ENABLED=false
# WHATSAPP_MODE=self-chat
# WHATSAPP_ALLOWED_USERS=15551234567
# WHATSAPP_REQUIRE_MENTION=
# WHATSAPP_FREE_RESPONSE_CHATS=
# WHATSAPP_REPLY_PREFIX=
#
# Hermes is reached on the LAN via ods-hermes-proxy (Caddy sidecar) which
# verifies the ods-session cookie against dashboard-api's verify endpoint
# (forward_auth → HMAC signature check via ODS_SESSION_SECRET).
# Direct Hermes port is NOT bound to the host — only the proxy is LAN-facing.
# HERMES_PROXY_PORT=9120 # LAN entry — what users actually browse to
# HERMES_PROXY_UPSTREAM=ods-hermes:9119 # Where the proxy forwards (internal DNS)
# ODS_AUTH_UPSTREAM=ods-dashboard-api:3002 # Where forward_auth verifies sessions
# HERMES_PROXY_AUTH_DOCS_URL= # Optional help link on the auth-required page
# Tailscale (Remote Access)
# ═══════════════════════════════════════════════════════════════════
# Optional remote-access via Tailscale's mesh VPN. Generate an auth
# key at https://login.tailscale.com/admin/settings/keys and paste
# below. Once joined the device is reachable as <hostname>.<tailnet>.ts.net
# from any other tailnet member.
#
# IMPORTANT: joining the tailnet alone isn't enough. For the device to
# actually answer HTTP at <hostname>.tail-xxxxx.ts.net, the host has to
# be listening for non-loopback traffic. That means:
# 1. ods-proxy is enabled (Caddy fielding port 80 + routing /chat,
# /api/*, /auth/* to backends)
# 2. BIND_ADDRESS=0.0.0.0 in this .env (loopback-only services don't
# accept tailnet packets even with network_mode: host)
# See docs/TAILSCALE.md for the full prerequisites and architecture.
#
# TS_AUTHKEY is consumed exactly once on first join. After that the
# tailscale daemon caches the node key in data/tailscale/, so you can
# rotate or delete the auth key in the Tailscale admin.
#
# TS_AUTHKEY=tskey-auth-xxxxxxxxxxxxxxxxxxxxxx
# TS_HOSTNAME= # Defaults to ODS_DEVICE_NAME
# TS_EXTRA_ARGS= # Optional, e.g. --advertise-tags=tag:ods