Skip to content

feat(creator): OmniVoice deploy unit for SPARK (Dockerfile + compose + make + acceptance) [validate-on-node] - #1845

Merged
POWERFULMOVES merged 1 commit into
mainfrom
feat/omnivoice-spark-deploy
Jun 20, 2026
Merged

POWERFULMOVES merged 1 commit into
mainfrom
feat/omnivoice-spark-deploy

Conversation

@POWERFULMOVES

Copy link
Copy Markdown
Owner

Summary

Turns the OmniVoice voice server (pmoves/services/creator-operator/omnivoice_server.py)
from a manual python omnivoice_server.py into a managed fleet service for the
SPARK node (NVIDIA DGX Spark, GB10 Grace-Blackwell, arm64 + CUDA, 128GB unified,
caps [cuda, comfyui, browser, voice]).

Files

File What
pmoves/services/creator-operator/Dockerfile.omnivoice Multiarch (amd64+arm64) image on nvidia/cuda runtime base (CUDA_BASE_TAG ARG). torch/torchaudio via ARG-driven index URL (TORCH_INDEX_URL, default cu128). GPU via the NVIDIA container runtime, not baked in. Binds 0.0.0.0:8002, /healthz HEALTHCHECK, no secrets baked. Build context = service dir (no services.common import).
pmoves/Makefile omnivoice-build / omnivoice-up / omnivoice-down targets driving the service-local compose under the voice profile.
pmoves/services/creator-operator/SPARK_DEPLOY.md Acceptance/validation doc mirroring ROCM_VALIDATION.md.

SPARK arm64-CUDA wheel TODO

SPARK is arm64, so the stock x86_64 cu128 torch wheel does not apply — it needs the
arm64/sbsa CUDA wheel (CUDA 12.8+). The exact wheel tag / index URL is left as
TODO-confirm-on-node
(not guessed); the Dockerfile install is ARG-driven
(TORCH_INDEX_URL / TORCH_SPEC) so the operator overrides it on the node after grounding
nvidia-smi + uname -m. Mirrors how ROCM_VALIDATION.md handles the unknown ROCm wheel.

Compose file (operator action)

docker-compose*.yml paths are damage-control-protected (the compose Known Road class,
matched by basename — even service-local). The branch author could not write the
compose file in-session (the KNOWN_ROAD env bypass is self-grant-denied), so the
full paste-ready docker-compose.omnivoice.yml + the operator Known-Road steps are in
SPARK_DEPLOY.md § 3a, with an optional root-level fleet-compose integration in § 3c.
The compose YAML snippet is yaml.safe_load-validated.

Validate-on-SPARK scaffold (NOT GPU-tested)

There is no SPARK / arm64 / GPU in the authoring environment. The image was not
built
and the server not run or GPU-tested. This is a scaffold to validate on SPARK.
A "do not route live voice to SPARK until these pass" gate is in the doc; the smoke harness
reuses scripts/rocm_smoke.sh (node-agnostic) against the deployed :8002.

🤖 Generated with Claude Code

…cceptance) [validate-on-node]

Turn the OmniVoice voice server (omnivoice_server.py) from a manual
`python omnivoice_server.py` into a managed fleet service for the SPARK node
(NVIDIA DGX Spark, GB10 Grace-Blackwell, arm64 + CUDA, 128GB unified).

- Dockerfile.omnivoice: multiarch (amd64+arm64) on nvidia/cuda runtime base
  (CUDA_BASE_TAG ARG). torch/torchaudio installed via ARG-driven index URL
  (TORCH_INDEX_URL, default cu128); SPARK arm64 needs the arm64/sbsa CUDA wheel
  (TODO-confirm-on-node). GPU via the NVIDIA container runtime, not baked in.
  Binds 0.0.0.0:8002, /healthz HEALTHCHECK, no secrets baked.
- Makefile: omnivoice-build / omnivoice-up / omnivoice-down targets driving the
  service-local compose under the `voice` profile.
- SPARK_DEPLOY.md: acceptance/validation doc mirroring ROCM_VALIDATION.md —
  arm64/sbsa torch wheel swap (TODO-confirm-on-node), /healthz + token-gated
  /synthesize + 24kHz WAV smoke via scripts/rocm_smoke.sh pointed at :8002, a
  "do not route live voice to SPARK until these pass" gate, and a P7/PBnJ launch
  section (pbnj/ tree is Pinokio-side, not in repo).

The compose service (docker-compose.omnivoice.yml) is a damage-control-protected
`docker-compose*.yml` path (compose Known Road, matched by basename even when
service-local). It could not be written in-session without the KNOWN_ROAD env,
so the full paste-ready YAML + the operator Known-Road steps live in
SPARK_DEPLOY.md § 3a (plus an optional root-level fleet-compose integration in § 3c).

Scaffold only: no SPARK/arm64/GPU in the authoring environment. Image NOT built,
server NOT run or GPU-tested here. All node-specific steps are TODO-confirm-on-node.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@coderabbitai

coderabbitai Bot commented Jun 20, 2026

Copy link
Copy Markdown
Contributor

Warning

Review limit reached

@POWERFULMOVES, we couldn't start this review because you've reached your PR review rate limit.

More reviews will be available in 36 minutes and 39 seconds. Learn how PR review limits work.

Your organization has used up its prepaid credits, and credit purchases are no longer available. Enable the review add-on in the billing tab to keep reviews running — you're only billed for reviews past your plan's rate limits ($0.25/file).

⌛ How to resolve this issue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based credits.

🚦 How do rate limits work?

CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan refill rate.

For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, the refill rate gradually slows as usage increases. The highest same-day bursts are limited more strictly.

Please see our Fair Usage Limits Policy for further information.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: 33c1ca92-6d6c-4e88-b3e0-eac15d026d80

📥 Commits

Reviewing files that changed from the base of the PR and between e49788a and 5774941.

📒 Files selected for processing (3)
  • pmoves/Makefile
  • pmoves/services/creator-operator/Dockerfile.omnivoice
  • pmoves/services/creator-operator/SPARK_DEPLOY.md
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/omnivoice-spark-deploy

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@github-actions

Copy link
Copy Markdown
Contributor

Docker Hardening Validation

Hardening Validation Report

Validated: Sat Jun 20 04:15:49 UTC 2026

Services Checked

PMOVES.AI Docker Hardening Validation

[INFO] Checking: pmoves/docker-compose.hardened.yml

[INFO] Validating: hi-rag-gateway-v2
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: extract-worker
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: langextract
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: presign
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: render-webhook
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: retrieval-eval
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: pdf-ingest
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: jellyfin-bridge
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: invidious-companion-proxy
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: ffmpeg-whisper
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: media-video
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: media-audio
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: hi-rag-gateway-v2-gpu
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: hi-rag-gateway-gpu
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: deepresearch
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: supaserch
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: publisher-discord
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: mesh-agent
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: nats-echo-req
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: nats-echo-res
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: comfy-watcher
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: grayjay-plugin-host
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: agent-zero
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: archon
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: channel-monitor
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: pmoves-yt
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: notebook-sync
[PASS] Non-root user: 65532:65532
[PASS] Read-only filesystem
[PASS] All capabilities dropped
[PASS] No-new-privileges enabled
[WARN] No resource limits

[INFO] Validating: supabase_service_role_key
[WARN] No user directive
[WARN] No read_only directive
[WARN] No cap_drop: ["ALL"]
[WARN] No no-new-privileges
[WARN] No resource limits

[INFO] Validating: supabase_jwt_secret
[WARN] No user directive
[WARN] No read_only directive
[WARN] No cap_drop: ["ALL"]
[WARN] No no-new-privileges
[WARN] No resource limits

======================================
Summary: 108 passed, 37 warnings, 0 errors

@POWERFULMOVES
POWERFULMOVES merged commit e7ad11c into main Jun 20, 2026
28 checks passed
@POWERFULMOVES
POWERFULMOVES deleted the feat/omnivoice-spark-deploy branch June 20, 2026 04:17

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 5774941f7e

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread pmoves/Makefile

.PHONY: omnivoice-build omnivoice-up omnivoice-down
omnivoice-build: ## Build the OmniVoice voice-server image (amd64 default; pass OMNIVOICE_PLATFORM=linux/arm64 for SPARK)
@test -f "$(OMNIVOICE_COMPOSE)" || (echo "✖ $(OMNIVOICE_COMPOSE) missing — operator must install it from SPARK_DEPLOY.md (compose Known Road)" && exit 1)

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Commit the compose file used by the targets

In a clean checkout these new omnivoice-build/omnivoice-up targets fail before doing any work because $(OMNIVOICE_COMPOSE) points at services/creator-operator/docker-compose.omnivoice.yml, but that file is not tracked or generated here (I checked git ls-files '*docker-compose.omnivoice.yml'/fd; only references are in this Makefile and the deploy doc). That makes the advertised Make entry points unusable unless every operator manually creates an untracked file first, so the deploy unit is incomplete in the repo.

Useful? React with 👍 / 👎.

Comment on lines +61 to +62
docker compose -f services/creator-operator/docker-compose.omnivoice.yml --profile voice build \
--build-arg OMNIVOICE_TORCH_INDEX_URL=<arm64-sbsa-cu12x-index> # TODO-confirm-on-node

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Pass the Dockerfile ARG name in the SPARK build command

When an operator follows this command to select the arm64/sbsa wheel, the override is a no-op: Docker/Compose --build-arg sets Dockerfile build-time variables by name, but Dockerfile.omnivoice declares ARG TORCH_INDEX_URL, not OMNIVOICE_TORCH_INDEX_URL (the compose snippet only maps that env var during interpolation). On SPARK this leaves the default x86 cu128 index in place and the build still tries the incompatible wheel; use --build-arg TORCH_INDEX_URL=... or set OMNIVOICE_TORCH_INDEX_URL=... in the shell before invoking Compose.

Useful? React with 👍 / 👎.

POWERFULMOVES added a commit that referenced this pull request Jun 24, 2026
…#1846)

* feat(creator): commit real OmniVoice compose file (omnivoice.compose.yml)

#1845 left the compose as a doc snippet because docker-compose*.yml is guard-
protected by basename. Fix: name it omnivoice.compose.yml (outside the glob) and
commit it for real, so 'make -C pmoves omnivoice-up' works without the operator
hand-pasting from SPARK_DEPLOY.md. Repoints OMNIVOICE_COMPOSE to the new path.
Service unchanged (omnivoice-server, :8002, GPU reservation, HF cache volume,
profiles creator/voice, OMNIVOICE_PLATFORM arm64 hook for SPARK).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

* fix(omnivoice): default bind 0.0.0.0 so in-stack flute-gateway can reach it

Codex P2: flute-gateway normalizes OMNIVOICE_URL 127.0.0.1 ->
host.docker.internal (main.py:183), which on Linux/bridge Docker resolves
to the host gateway interface, not loopback — so a 127.0.0.1-published
OmniVoice port was unreachable from the flute-gateway container, breaking
the default in-stack deployment unless every operator overrode the bind.
Default to 0.0.0.0 (access gated by OMNIVOICE_TOKEN); operators on exposed
nodes with no in-container consumer can still set OMNIVOICE_BIND=127.0.0.1.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

---------

Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
POWERFULMOVES added a commit that referenced this pull request Aug 5, 2026
…lines (#2402)

The village-gate 3-policy fix (#2285) left only the USER/useradd/CMD tail
(in the wrong order: USER before useradd) and deleted the entire build —
FROM, torch install, requirements, server COPY, healthcheck — making
'no build stage in current context' the omnivoice-build/up failure.
Restored the original 89-line deploy unit from #1845 and applied the
policy the gate wanted PROPERLY: useradd before USER, cache/app ownership
so the HF download can write, non-root at runtime.

Found while standing up the set-not-preset voice vessels (OmniVoice =
ref_audio catalog + instruct voice design).

Co-authored-by: Mavis <Mavis@pmoves.local>
Co-authored-by: Claude Fable 5 <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant