# Self-contained compose for Sanad Package 1 (Basic Communication). # NO sibling folders, NO sanad-base — the Sanad engine is vendored in ./vendor. # This file + this directory are all you need to build and run P1. # # docker compose up -d --build # build + run -> http://:8011 # docker compose logs -f # view logs # docker compose down # stop # # Jetson Docker without buildx: DOCKER_BUILDKIT=0 docker compose up -d --build # # Audio: SANAD_AUDIO_PROFILE=builtin (G1 chest, needs the Unitree SDK baked at # build) | plugged (USB/Anker via PulseAudio, no SDK needed) # License: point SANAD_LICENSE_FILE at your signed sanad.lic (default = example). # Language: set SANAD_LANGUAGE, or via the license `language` feature, or persona. services: p1: build: context: . dockerfile: Dockerfile args: BASE_OS_IMAGE: "${BASE_OS_IMAGE:-python:3.10-slim-bookworm}" WITH_UNITREE_SDK: "${WITH_UNITREE_SDK:-1}" image: "${SANAD_IMAGE:-sanad-p1:latest}" container_name: sanad-p1 # Host networking REQUIRED — the G1 DDS link + Gemini cloud + chest audio. network_mode: host # `unless-stopped` survives reboot (with `sudo systemctl enable docker`). restart: unless-stopped environment: SANAD_PACKAGE: P1 SANAD_DASHBOARD_PORT: "8011" SANAD_DASHBOARD_HOST: "0.0.0.0" SANAD_VOICE_BRAIN: gemini SANAD_AUDIO_PROFILE: "${SANAD_AUDIO_PROFILE:-builtin}" # builtin (chest) | plugged (USB/Anker) SANAD_DDS_INTERFACE: "${SANAD_DDS_INTERFACE:-eth0}" # Plugged/Bluetooth audio (Anker USB, JBL BT) route through the HOST # PulseAudio server — chest ("builtin") uses DDS and needs none of this. PULSE_SERVER: "${PULSE_SERVER:-unix:/run/user/1000/pulse/native}" PULSE_COOKIE: "${PULSE_COOKIE:-/run/user/1000/pulse/cookie}" # root→uid-1000 PA auth SANAD_LICENSE: /etc/sanad/sanad.lic SANAD_PUBKEY: /etc/sanad/pubkey.ed25519 SANAD_LICENSE_BIND: "${SANAD_LICENSE_BIND:-0}" # 1 = enforce machine fingerprint SANAD_LANGUAGE: "${SANAD_LANGUAGE:-}" devices: - "/dev/snd:/dev/snd" # USB/plugged audio (Anker) via ALSA/Pulse volumes: - "${SANAD_LICENSE_FILE:-./license/sanad.lic.example}:/etc/sanad/sanad.lic:ro" # Plugged/Bluetooth audio (Anker/JBL): mount the host PulseAudio runtime dir # (socket + auth cookie) so the container sets ANY sink's volume/output — the # volume slider then drives chest (DDS) AND plugged (PA), exactly like SanadV3. # Chest ("builtin") audio uses DDS only and needs none of this. One-time host # setup for a stable boot-time socket: `loginctl enable-linger unitree`. - "${SANAD_PULSE_DIR:-/run/user/1000/pulse}:/run/user/1000/pulse" - "./data:/app/Sanad/data" # persist persona/recordings/config on host # Bound license (SANAD_LICENSE_BIND=1) also needs the host machine-id so the # in-container fingerprint matches the host — uncomment: # - "/etc/machine-id:/etc/machine-id:ro"