-
Notifications
You must be signed in to change notification settings - Fork 13
Expand file tree
/
Copy pathdocker-compose.yml.template
More file actions
107 lines (107 loc) · 6.83 KB
/
Copy pathdocker-compose.yml.template
File metadata and controls
107 lines (107 loc) · 6.83 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
services:
xiaozhi-esp32-server:
build:
context: .
dockerfile: Dockerfile
image: xiaozhi-esp32-server-piper:local
container_name: xiaozhi-esp32-server
restart: unless-stopped
# --- BEGIN CUDA BLOCK (removed by `make setup` if no NVIDIA runtime) ---
# GPU access for WhisperLocal ASR (faster-whisper float16 needs CUDA).
# Requires nvidia-container-toolkit on the host.
#
# ASR ONLY — this has nothing to do with the LLM. A CPU-only host is fine:
# `make setup` drops this block and selects FunASR (CPU) instead. Serving
# models from a GPU on another machine (LM Studio, Ollama, llama-swap) needs
# no GPU here at all — see docs/llm-backends.md.
runtime: nvidia
deploy:
resources:
reservations:
devices:
- driver: nvidia
count: all
capabilities: [gpu]
# --- END CUDA BLOCK ---
environment:
# --- BEGIN CUDA ENV (removed by `make setup` if no NVIDIA runtime) ---
- NVIDIA_VISIBLE_DEVICES=all
- NVIDIA_DRIVER_CAPABILITIES=compute,utility
# --- END CUDA ENV ---
- TZ=<TZ_VALUE>
# EDIT: set to the dotty-behaviour service URL for vision intent handling.
# dotty-behaviour runs on the same host; use the host LAN IP, not loopback
# (this container is on a bridge network, so 127.0.0.1 resolves to itself).
- VISION_BRIDGE_URL=http://<XIAOZHI_HOST>:8090
# Active persona file under ./personas/ (loaded by the LLM provider).
# Currently fixed to "default" — smart.md exists for manual swap when you
# want an adult-framed persona on the smart-mode cloud path.
- PERSONA=default
# kid_mode / smart_mode toggle state — receiveAudioHandle.py READS these
# to paint the firmware LED pips on reconnect; the bridge dashboard WRITES
# them. Both containers must point at the SAME files, so this path is
# bind-mounted (below, read-only) from the bridge's state dir. Without
# this the reader falls through to the dead /root/zeroclaw-bridge default
# and the firmware pips desync from the dashboard on every reconnect.
- DOTTY_KID_MODE_STATE=/var/lib/dotty-bridge/state/kid-mode
- DOTTY_SMART_MODE_STATE=/var/lib/dotty-bridge/state/smart-mode
# Shared admin-API secret (X-Admin-Token). Read from ./.env — `make
# setup` generates it. Unset/empty = permissive (admin routes open);
# set = this server enforces it AND every caller (bridge,
# dotty-behaviour, dotty-pi) must carry the same value in its own
# .env. See .env.example.
- DOTTY_ADMIN_TOKEN=${DOTTY_ADMIN_TOKEN:-}
ports:
- "8000:8000"
- "8003:8003"
volumes:
- ./data/.config.yaml:/opt/xiaozhi-esp32-server/data/.config.yaml:ro
- ./models/SenseVoiceSmall:/opt/xiaozhi-esp32-server/models/SenseVoiceSmall
- ./tmp:/opt/xiaozhi-esp32-server/tmp
- ./custom-providers/openai_compat:/opt/xiaozhi-esp32-server/core/providers/llm/openai_compat
- ./custom-providers/pi_voice:/opt/xiaozhi-esp32-server/core/providers/llm/pi_voice
# PiVoiceLLM shells out to `docker exec -i dotty-pi pi --mode rpc ...`,
# so this container needs the docker CLI binary AND the host docker
# socket. WARNING: mounting /var/run/docker.sock gives this container
# effective root on the docker host (it can `docker run --privileged
# anything`). Acceptable for a single-purpose self-hosted appliance;
# do not enable on a multi-tenant host. Required for `selected_module.LLM:
# PiVoiceLLM` — comment both lines out if running OpenAICompat.
- /var/run/docker.sock:/var/run/docker.sock
- /usr/bin/docker:/usr/bin/docker:ro
- ./personas:/opt/xiaozhi-esp32-server/personas:ro
- ./custom-providers/edge_stream/edge_stream.py:/opt/xiaozhi-esp32-server/core/providers/tts/edge_stream.py:ro
- ./custom-providers/piper_local/piper_local.py:/opt/xiaozhi-esp32-server/core/providers/tts/piper_local.py:ro
- ./models/piper:/opt/xiaozhi-esp32-server/models/piper:ro
- ./custom-providers/asr/fun_local.py:/opt/xiaozhi-esp32-server/core/providers/asr/fun_local.py:ro
- ./custom-providers/asr/whisper_local.py:/opt/xiaozhi-esp32-server/core/providers/asr/whisper_local.py:ro
- ./models/whisper-small.en-ct2:/opt/xiaozhi-esp32-server/models/whisper-small.en-ct2:ro
- ./custom-providers/asr/sensevoice_onnx.py:/opt/xiaozhi-esp32-server/core/providers/asr/sensevoice_onnx.py:ro
- ./models/SenseVoiceSmall-onnx:/opt/xiaozhi-esp32-server/models/SenseVoiceSmall-onnx:ro
- ./receiveAudioHandle.py:/opt/xiaozhi-esp32-server/core/handle/receiveAudioHandle.py:ro
- ./dances.py:/opt/xiaozhi-esp32-server/core/handle/dances.py:ro
- ./custom-providers/textUtils.py:/opt/xiaozhi-esp32-server/core/utils/textUtils.py:ro
# DOTTY DeviceCommand seam: MCP request ids + envelope + per-conn
# serialized sends, shared by http_server.py + receiveAudioHandle.py
- ./custom-providers/xiaozhi-patches/device_command.py:/opt/xiaozhi-esp32-server/core/utils/device_command.py:ro
- ./songs:/opt/xiaozhi-esp32-server/config/assets/songs:ro
# DOTTY portal: admin /inject-text route + active-connection registry
- ./custom-providers/xiaozhi-patches/portal_bridge.py:/opt/xiaozhi-esp32-server/core/portal_bridge.py:ro
- ./custom-providers/xiaozhi-patches/websocket_server.py:/opt/xiaozhi-esp32-server/core/websocket_server.py:ro
- ./custom-providers/xiaozhi-patches/http_server.py:/opt/xiaozhi-esp32-server/core/http_server.py:ro
# DOTTY ambient perception: relay firmware "event" frames to the bridge
- ./custom-providers/xiaozhi-patches/textMessageHandlerRegistry.py:/opt/xiaozhi-esp32-server/core/handle/textMessageHandlerRegistry.py:ro
# DOTTY OTA: patched ota_handler that composes the firmware download URL
# directly from local_ip+http_port instead of doing a string-replace on
# `vision_explain` (which only worked when vision lived at the canonical
# `/mcp/vision/explain` path; our setup points it at the dotty-behaviour service).
- ./custom-providers/xiaozhi-patches/ota_handler.py:/opt/xiaozhi-esp32-server/core/api/ota_handler.py:ro
# OTA artifact directory — drop m5stack-stack-chan_<version>.bin here
# and the device polls + self-flashes on next boot. See docs/ota-verification.md.
- ./data/bin:/opt/xiaozhi-esp32-server/data/bin
# Shared kid/smart-mode toggle state (READ-ONLY here — the bridge
# dashboard owns writes). Host path MUST match the bridge container's
# state mount (bridge/docker-compose.yml → /var/lib/dotty-bridge/state).
# Override DOTTY_STATE_DIR if your bridge writes elsewhere. Keeps the
# firmware kid/smart LED pips in sync with the dashboard across reconnects.
- ${DOTTY_STATE_DIR:-/mnt/user/appdata/dotty-bridge/state}:/var/lib/dotty-bridge/state:ro