rebrand: rename VoiceBox to TalkBox throughout codebase
CI / frontend-quality (push) Canceled after 0s

- All 'voicebox'/'Voicebox'/'VOICEBOX' strings replaced with 'talkbox'/'TalkBox'/'TALKBOX'
- Port changed from 17493 to 17494 (avoids conflict with upstream VoiceBox)
- MCP tool namespace: voicebox.* -> talkbox.*
- App bundle ID: sh.voicebox.app -> com.talkbox.app
- Binary names: voicebox-server -> talkbox-server, voicebox-mcp -> talkbox-mcp
- Docker user/group: voicebox -> talkbox
- Database: voicebox.db -> talkbox.db
- Env vars: VOICEBOX_* -> TALKBOX_*
- Asset files renamed: voicebox-logo.* -> talkbox-logo.*, etc.
- External binaries in tauri.conf.json updated to talkbox-server/talkbox-mcp
This commit is contained in:
2026-08-24 19:45:56 -07:00
parent eaef8dd838
commit b8815e94ea
205 changed files with 1593 additions and 1593 deletions
+8 -8
View File
@@ -48,10 +48,10 @@ Search order — **first hit wins**:
| Platform | Path | Build type |
|----------|------|------------|
| macOS | `backend/dist/voicebox-server-cuda/voicebox-server-cuda` | onedir (CUDA, rarely on Mac) |
| macOS | `backend/dist/voicebox-server` | onefile (CPU) |
| Windows | `backend\dist\voicebox-server-cuda\voicebox-server-cuda.exe` | onedir (CUDA) |
| Windows | `backend\dist\voicebox-server.exe` | onefile (CPU) |
| macOS | `backend/dist/talkbox-server-cuda/talkbox-server-cuda` | onedir (CUDA, rarely on Mac) |
| macOS | `backend/dist/talkbox-server` | onefile (CPU) |
| Windows | `backend\dist\talkbox-server-cuda\talkbox-server-cuda.exe` | onedir (CUDA) |
| Windows | `backend\dist\talkbox-server.exe` | onefile (CPU) |
If none exist, run `python backend/build_binary.py` and wait for it to finish (can take 5-20 min). Fail with a clear error if the build itself fails. `--skip-build` flag forces "error out if no binary" instead of building.
@@ -64,7 +64,7 @@ Mirrors Tauri's launch in `tauri/src-tauri/src/main.rs:369-388`:
```
- **Port**: bind to `0` first in Python to grab a free port, then pass that number.
- **Data dir**: `tempfile.mkdtemp(prefix="voicebox-e2e-")`. Deleted after the run unless `--keep-data-dir`. Profiles and generated WAVs land here.
- **Data dir**: `tempfile.mkdtemp(prefix="talkbox-e2e-")`. Deleted after the run unless `--keep-data-dir`. Profiles and generated WAVs land here.
- **Parent PID**: current Python PID — ensures the backend dies if the test crashes (watchdog in `server.py:102-224`).
- **stdout/stderr**: tee to both a log file in `./results/server-<timestamp>.log` and a rolling in-memory buffer. On model failure, last 100 lines of the buffer are attached to that model's error record.
@@ -136,7 +136,7 @@ On timeout: cancel the SSE stream, mark the row `timeout`, and continue to the n
```json
{
"platform": "darwin-arm64",
"binary": "/abs/path/voicebox-server",
"binary": "/abs/path/talkbox-server",
"binary_size_mb": 612,
"started_at": "2026-04-16T12:34:56Z",
"finished_at": "...",
@@ -160,7 +160,7 @@ On timeout: cancel the SSE stream, mark the row `timeout`, and continue to the n
Companion `./results/e2e-<...>.md`:
```
# Voicebox E2E — darwin-arm64 — 2026-04-16 12:34
# TalkBox E2E — darwin-arm64 — 2026-04-16 12:34
| Engine | Size | Status | Elapsed | Error |
|---------------------|------|--------|---------|-------|
@@ -208,7 +208,7 @@ The script uses only stdlib + `httpx` (or `requests`) + `sseclient-py` — all a
- Always kill the spawned binary in a `try/finally`. On Windows, `taskkill /F /T` the whole tree (Tauri does the same).
- Verify the port is free on shutdown (Tauri port-reuse check in `main.rs:114-186` could otherwise pick up a ghost).
- Don't touch the user's HF cache by default — let the server use `HF_HUB_CACHE` / `VOICEBOX_MODELS_DIR`. Passing `--isolated-cache` would point both env vars at the tempdir for a true cold-start run (opt-in only; would re-download every time).
- Don't touch the user's HF cache by default — let the server use `HF_HUB_CACHE` / `TALKBOX_MODELS_DIR`. Passing `--isolated-cache` would point both env vars at the tempdir for a true cold-start run (opt-in only; would re-download every time).
## Non-goals
+1 -1
View File
@@ -1,5 +1,5 @@
"""
Test suite for Voicebox backend.
Test suite for TalkBox backend.
This directory contains manual test scripts for debugging and validating
progress tracking, model downloads, and generation functionality.
+6 -6
View File
@@ -96,8 +96,8 @@ def find_binary() -> Optional[Path]:
is_win = platform.system() == "Windows"
exe = ".exe" if is_win else ""
candidates = [
DIST_DIR / "voicebox-server-cuda" / f"voicebox-server-cuda{exe}",
DIST_DIR / f"voicebox-server{exe}",
DIST_DIR / "talkbox-server-cuda" / f"talkbox-server-cuda{exe}",
DIST_DIR / f"talkbox-server{exe}",
]
for c in candidates:
if c.exists() and c.is_file():
@@ -381,7 +381,7 @@ def write_reports(
json_path.write_text(json.dumps(doc, indent=2))
lines = [
f"# Voicebox E2E — {plat}{started_at.strftime('%Y-%m-%d %H:%M UTC')}",
f"# TalkBox E2E — {plat}{started_at.strftime('%Y-%m-%d %H:%M UTC')}",
"",
f"Binary: `{binary}` ",
f"Elapsed: {doc['elapsed_seconds']:.1f}s",
@@ -424,8 +424,8 @@ def write_reports(
# ── Main ─────────────────────────────────────────────────────────────
def parse_args() -> argparse.Namespace:
p = argparse.ArgumentParser(description="Voicebox E2E model generation test")
p.add_argument("--binary", type=Path, help="Path to voicebox-server binary (overrides auto-detect)")
p = argparse.ArgumentParser(description="TalkBox E2E model generation test")
p.add_argument("--binary", type=Path, help="Path to talkbox-server binary (overrides auto-detect)")
p.add_argument("--skip-build", action="store_true", help="Error if binary missing instead of building")
p.add_argument(
"--reference-wav",
@@ -516,7 +516,7 @@ def main() -> int:
print(f"[fixture] reference text: {ref_text!r}", flush=True)
# Tempdir + log path
data_dir = Path(tempfile.mkdtemp(prefix="voicebox-e2e-"))
data_dir = Path(tempfile.mkdtemp(prefix="talkbox-e2e-"))
args.output_dir.mkdir(parents=True, exist_ok=True)
ts = datetime.now(timezone.utc).strftime("%Y%m%d-%H%M%S")
log_path = args.output_dir / f"server-{ts}.log"
+7 -7
View File
@@ -2,7 +2,7 @@
Tests for CORS origin restrictions.
Validates that the CORS middleware only allows known local origins
and respects the VOICEBOX_CORS_ORIGINS environment variable.
and respects the TALKBOX_CORS_ORIGINS environment variable.
Uses a minimal FastAPI app that mirrors the exact CORS configuration
from backend/main.py, so tests run without heavy ML dependencies.
@@ -32,8 +32,8 @@ def _build_app(env_origins: str = "") -> FastAPI:
_default_origins = [
"http://localhost:5173",
"http://127.0.0.1:5173",
"http://localhost:17493",
"http://127.0.0.1:17493",
"http://localhost:17494",
"http://127.0.0.1:17494",
"tauri://localhost",
"https://tauri.localhost",
]
@@ -88,8 +88,8 @@ class TestCORSDefaultOrigins:
@pytest.mark.parametrize("origin", [
"http://localhost:5173",
"http://127.0.0.1:5173",
"http://localhost:17493",
"http://127.0.0.1:17493",
"http://localhost:17494",
"http://127.0.0.1:17494",
"tauri://localhost",
"https://tauri.localhost",
])
@@ -121,7 +121,7 @@ class TestCORSDefaultOrigins:
class TestCORSCustomOrigins:
"""VOICEBOX_CORS_ORIGINS env var should extend the allowlist."""
"""TALKBOX_CORS_ORIGINS env var should extend the allowlist."""
def test_custom_origin_allowed(self, client_with_custom_origins):
headers = _get_with_origin(client_with_custom_origins, "https://custom.example.com")
@@ -141,7 +141,7 @@ class TestCORSCustomOrigins:
class TestCORSEnvVarParsing:
"""Edge cases for VOICEBOX_CORS_ORIGINS parsing."""
"""Edge cases for TALKBOX_CORS_ORIGINS parsing."""
def test_empty_env_var(self):
app = _build_app("")
+1 -1
View File
@@ -1,4 +1,4 @@
"""Tests for the voicebox.speak MCP tool's ``model_size`` plumbing (issue #884).
"""Tests for the talkbox.speak MCP tool's ``model_size`` plumbing (issue #884).
The MCP speak path used to build its ``GenerationRequest`` without a
``model_size``, so every agent-triggered generation silently fell back to the
+8 -8
View File
@@ -45,7 +45,7 @@ class TestIsRocmFile:
@pytest.mark.parametrize(
"rel_path",
[
"voicebox-server-rocm.exe",
"talkbox-server-rocm.exe",
"_internal/python312.dll",
"_internal/torch/lib/torch_cpu.dll",
"_internal/torch/lib/c10.dll",
@@ -68,8 +68,8 @@ class TestPackage:
"""End-to-end split of a synthetic onedir into the two archives."""
def test_split_and_manifest(self, tmp_path):
onedir = tmp_path / "voicebox-server-rocm"
_write(onedir / "voicebox-server-rocm.exe")
onedir = tmp_path / "talkbox-server-rocm"
_write(onedir / "talkbox-server-rocm.exe")
_write(onedir / "_internal" / "python312.dll")
_write(onedir / "_internal" / "rocm_sdk" / "__init__.py")
_write(onedir / "_internal" / "torch" / "lib" / "torch_cpu.dll")
@@ -88,11 +88,11 @@ class TestPackage:
out = tmp_path / "release-assets"
package_rocm.package(onedir, out, "rocm7.2-v1", ">=2.9.0,<2.10.0")
server = out / "voicebox-server-rocm.tar.gz"
server = out / "talkbox-server-rocm.tar.gz"
libs = out / "rocm-libs-rocm7.2-v1.tar.gz"
assert server.exists()
assert libs.exists()
assert (out / "voicebox-server-rocm.tar.gz.sha256").exists()
assert (out / "talkbox-server-rocm.tar.gz.sha256").exists()
assert (out / "rocm-libs-rocm7.2-v1.tar.gz.sha256").exists()
with tarfile.open(libs) as tar:
@@ -106,15 +106,15 @@ class TestPackage:
"_internal/_rocm_sdk_libraries_custom/lib/rocblas/library/TensileLibrary.dat"
in lib_names
)
assert "voicebox-server-rocm.exe" in core_names
assert "talkbox-server-rocm.exe" in core_names
assert "_internal/torch/lib/torch_cpu.dll" in core_names
assert "_internal/rocm_sdk/__init__.py" in core_names
# Archives must be disjoint.
assert lib_names.isdisjoint(core_names)
def test_empty_rocm_set_exits(self, tmp_path):
onedir = tmp_path / "voicebox-server-rocm"
_write(onedir / "voicebox-server-rocm.exe")
onedir = tmp_path / "talkbox-server-rocm"
_write(onedir / "talkbox-server-rocm.exe")
_write(onedir / "_internal" / "torch" / "lib" / "torch_cpu.dll")
with pytest.raises(SystemExit):
+2 -2
View File
@@ -177,7 +177,7 @@ def score(
# ── Runner ────────────────────────────────────────────────────────────
DEFAULT_PORTS = (8000, 8765, 8899, 17493)
DEFAULT_PORTS = (8000, 8765, 8899, 17494)
THROWAWAY_PROFILE_PREFIX = "personality-harness-"
KOKORO_PROBE_VOICE = "af_heart"
"""Any valid kokoro voice id works — compose never calls into TTS, it
@@ -204,7 +204,7 @@ def detect_backend_port(hint: Optional[int]) -> int:
except Exception:
continue
raise SystemExit(
"No running Voicebox backend found. Start it (`python backend/main.py`) "
"No running TalkBox backend found. Start it (`python backend/main.py`) "
f"or pass --port. Tried: {candidates}"
)
+1 -1
View File
@@ -252,7 +252,7 @@ async def test_full_integration():
async def main():
"""Run all tests."""
print("\n" + "=" * 60)
print("Voicebox Progress Tracking Test Suite")
print("TalkBox Progress Tracking Test Suite")
print("=" * 60)
results = []
+4 -4
View File
@@ -15,7 +15,7 @@ Usage:
python backend/tests/test_refinement_samples.py
# Hit a non-default port (auto-detected via /health probe when omitted):
python backend/tests/test_refinement_samples.py --port 17493
python backend/tests/test_refinement_samples.py --port 17494
# Only test one model size:
python backend/tests/test_refinement_samples.py --model 4B
@@ -316,7 +316,7 @@ def score(sample: Sample, model: str, refined: str, latency_ms: int) -> Scorecar
# ── Runner ────────────────────────────────────────────────────────────
DEFAULT_PORTS = (8000, 8765, 8899, 17493)
DEFAULT_PORTS = (8000, 8765, 8899, 17494)
def detect_backend_port(hint: Optional[int]) -> int:
@@ -339,7 +339,7 @@ def detect_backend_port(hint: Optional[int]) -> int:
except Exception:
continue
raise SystemExit(
"No running Voicebox backend found. Start it (`python backend/main.py`) "
"No running TalkBox backend found. Start it (`python backend/main.py`) "
f"or pass --port. Tried: {candidates}"
)
@@ -407,7 +407,7 @@ def format_report(cards: list[Scorecard]) -> str:
def main() -> int:
ap = argparse.ArgumentParser(description=__doc__)
ap.add_argument("--port", type=int, default=None,
help="Voicebox backend port (auto-detected if omitted)")
help="TalkBox backend port (auto-detected if omitted)")
ap.add_argument("--model", choices=("0.6B", "1.7B", "4B"), action="append",
help="Refinement model size(s) to test (repeat to run several)")
ap.add_argument("--json", type=Path, default=None,
+3 -3
View File
@@ -35,7 +35,7 @@ class TestRocmBuildArgs:
def test_binary_name(self, captured_args):
idx = captured_args.index("--name")
assert captured_args[idx + 1] == "voicebox-server-rocm"
assert captured_args[idx + 1] == "talkbox-server-rocm"
def test_pack_mode_is_onedir(self, captured_args):
assert "--onedir" in captured_args
@@ -91,8 +91,8 @@ class TestRocmBuildE2E:
backend_dir = Path(__file__).parent.parent
build_script = backend_dir / "build_binary.py"
dist_dir = backend_dir / "dist"
binary_dir = dist_dir / "voicebox-server-rocm"
binary_exe = binary_dir / "voicebox-server-rocm.exe"
binary_dir = dist_dir / "talkbox-server-rocm"
binary_exe = binary_dir / "talkbox-server-rocm.exe"
# Clean previous dist if it exists to ensure a fresh build
if binary_dir.exists():
+10 -10
View File
@@ -40,7 +40,7 @@ def fake_tar_gz():
buf = BytesIO()
with tarfile.open(fileobj=buf, mode="w:gz") as tar:
data = b"fake binary content"
info = tarfile.TarInfo(name="voicebox-server-rocm.exe")
info = tarfile.TarInfo(name="talkbox-server-rocm.exe")
info.size = len(data)
tar.addfile(info, BytesIO(data))
buf.seek(0)
@@ -137,18 +137,18 @@ async def test_download_rocm_binary_progress_reporting(mock_backends_dir, fake_t
libs_sha = hashlib.sha256(fake_tar_gz).hexdigest()
responses = {
"https://github.com/jamiepine/voicebox/releases/download/v0.2.3/voicebox-server-rocm.tar.gz": FakeResponse(
"https://github.com/jamiepine/talkbox/releases/download/v0.2.3/talkbox-server-rocm.tar.gz": FakeResponse(
content=fake_tar_gz,
headers={"content-length": str(len(fake_tar_gz))},
),
"https://github.com/jamiepine/voicebox/releases/download/v0.2.3/voicebox-server-rocm.tar.gz.sha256": FakeResponse(
content=f"{server_sha} voicebox-server-rocm.tar.gz\n".encode(),
"https://github.com/jamiepine/talkbox/releases/download/v0.2.3/talkbox-server-rocm.tar.gz.sha256": FakeResponse(
content=f"{server_sha} talkbox-server-rocm.tar.gz\n".encode(),
),
f"https://github.com/jamiepine/voicebox/releases/download/v0.2.3/rocm-libs-{rocm.ROCM_LIBS_VERSION}.tar.gz": FakeResponse(
f"https://github.com/jamiepine/talkbox/releases/download/v0.2.3/rocm-libs-{rocm.ROCM_LIBS_VERSION}.tar.gz": FakeResponse(
content=fake_tar_gz,
headers={"content-length": str(len(fake_tar_gz))},
),
f"https://github.com/jamiepine/voicebox/releases/download/v0.2.3/rocm-libs-{rocm.ROCM_LIBS_VERSION}.tar.gz.sha256": FakeResponse(
f"https://github.com/jamiepine/talkbox/releases/download/v0.2.3/rocm-libs-{rocm.ROCM_LIBS_VERSION}.tar.gz.sha256": FakeResponse(
content=f"{libs_sha} rocm-libs.tar.gz\n".encode(),
),
}
@@ -160,7 +160,7 @@ async def test_download_rocm_binary_progress_reporting(mock_backends_dir, fake_t
# Verify extraction
rocm_dir = rocm.get_rocm_dir()
assert (rocm_dir / "voicebox-server-rocm.exe").exists()
assert (rocm_dir / "talkbox-server-rocm.exe").exists()
# Verify manifest written
manifest_path = rocm.get_rocm_libs_manifest_path()
@@ -177,13 +177,13 @@ async def test_download_rocm_binary_progress_reporting(mock_backends_dir, fake_t
@pytest.mark.asyncio
async def test_is_rocm_active(mock_backends_dir, monkeypatch):
monkeypatch.setenv("VOICEBOX_BACKEND_VARIANT", "rocm")
monkeypatch.setenv("TALKBOX_BACKEND_VARIANT", "rocm")
assert rocm.is_rocm_active() is True
monkeypatch.setenv("VOICEBOX_BACKEND_VARIANT", "cpu")
monkeypatch.setenv("TALKBOX_BACKEND_VARIANT", "cpu")
assert rocm.is_rocm_active() is False
monkeypatch.delenv("VOICEBOX_BACKEND_VARIANT", raising=False)
monkeypatch.delenv("TALKBOX_BACKEND_VARIANT", raising=False)
assert rocm.is_rocm_active() is False
+2 -2
View File
@@ -65,8 +65,8 @@ class TestRocmRequirements:
@pytest.mark.timeout(900)
@pytest.mark.skipif(
not os.environ.get("VOICEBOX_TEST_ROCM_INSTALL"),
reason="Set VOICEBOX_TEST_ROCM_INSTALL=1 to run the heavy install test",
not os.environ.get("TALKBOX_TEST_ROCM_INSTALL"),
reason="Set TALKBOX_TEST_ROCM_INSTALL=1 to run the heavy install test",
)
def test_rocm_torch_installs_and_detects_amd(self, backend_dir):
"""