fix(worker): preserve isolated OmniVoice synthesis settings

This commit is contained in:
Palash Debnath
2026-08-28 19:32:20 +05:30
parent 3b6e15dad5
commit 1e4fdd12e0
4 changed files with 66 additions and 4 deletions
+17 -3
View File
@@ -208,9 +208,11 @@ class TaskExecutor:
from services.text_normalization import normalize_for_tts
text = normalize_for_tts(row.get("text") or "", row.get("language"))
seed = None
if row.get("seed") is not None:
import torch
torch.manual_seed(int(row["seed"]))
seed = int(row["seed"])
torch.manual_seed(seed)
kwargs = {
"language": row.get("language") if row.get("language") != "Auto" else None,
"ref_audio": row.get("ref_audio"), "ref_text": row.get("ref_text"),
@@ -221,6 +223,11 @@ class TaskExecutor:
"speed": float(row.get("speed") or 1.0), "denoise": True,
"postprocess_output": True,
}
if (
getattr(backend, "supports_native_omnivoice_controls", False)
and seed is not None
):
kwargs["seed"] = seed
audio = backend.generate(text=text, **kwargs)
preset = row.get("effect_preset") or "broadcast"
if preset != "raw":
@@ -332,7 +339,10 @@ class TaskExecutor:
key: value for key, value in opts.to_manifest().items()
if value is not None and key not in ("seed", "vary_repeats")
}
if isinstance(backend, OmniVoiceBackend):
native_proxy = bool(
getattr(backend, "supports_native_omnivoice_controls", False)
)
if isinstance(backend, OmniVoiceBackend) or native_proxy:
extra.setdefault("num_step", 32)
extra.setdefault("guidance_scale", 2.0)
for key in ("emo_vector", "emo_text", "emo_alpha"):
@@ -341,11 +351,13 @@ class TaskExecutor:
def synth(text, index, speed=None):
voice = voices[int(index)]
base_seed = opts.seed if opts.seed is not None else voice.get("seed")
seed = None
if base_seed is not None:
import torch
nonce = occurrence["value"] if opts.vary_repeats else 0
occurrence["value"] += 1
torch.manual_seed(segment_seed(base_seed, text, nonce))
seed = segment_seed(base_seed, text, nonce)
torch.manual_seed(seed)
kwargs = {
"language": language,
"ref_audio": voice.get("ref_audio"),
@@ -354,6 +366,8 @@ class TaskExecutor:
"speed": float(speed) if speed else 1.0,
**extra,
}
if native_proxy and seed is not None:
kwargs["seed"] = seed
return backend.generate(text, **kwargs)
spans = [Span(voice_id=str(i), text=row.get("text", ""),
+1 -1
View File
@@ -32,7 +32,7 @@ lower call overhead.
## Selecting it
- **Settings -> Engines**, or
- **Model Catalogue → Engines**, or
- `OMNIVOICE_TTS_BACKEND=omnivoice-subprocess`
The explicit engine is opt-in on CUDA, ROCm, and CPU. Apple Silicon gets the
+27
View File
@@ -54,3 +54,30 @@ def test_audiobook_worker_marks_and_encodes_chapter(monkeypatch):
)
assert len(audio) == 20
assert marked == [(100, "worker.executor.tts")]
def test_audiobook_worker_forwards_mps_proxy_quality_and_seed():
import numpy as np
from services.audiobook import segment_seed
from worker.executor import TaskExecutor
calls = []
class Backend:
sample_rate = 100
supports_native_omnivoice_controls = True
def generate(self, text, **kwargs):
calls.append((text, kwargs))
return np.ones(20, dtype=np.float32)
TaskExecutor._synthesize_audiobook(
Backend(), [{"text": "hello", "pause_ms_after": 0}],
[{"ref_text": None, "instruct": None, "seed": 42}],
{"ref_audio": [None], "expressive": {}, "watermark": False},
)
_text, kwargs = calls[0]
assert kwargs["num_step"] == 32
assert kwargs["guidance_scale"] == 2.0
assert kwargs["seed"] == segment_seed(42, "hello")
+21
View File
@@ -83,6 +83,27 @@ class _FakeBackend:
type(self).unloaded += 1
def test_dub_worker_forwards_seed_into_mps_proxy():
calls = []
class Proxy:
sample_rate = 24_000
applies_own_mastering = False
supports_native_omnivoice_controls = True
def generate(self, text, **kwargs):
calls.append((text, kwargs))
import torch
return torch.zeros(1, 240)
TaskExecutor._synthesize_dub_segment(Proxy(), {
"text": "hello", "seed": 123, "effect_preset": "raw",
})
assert calls[0][1]["seed"] == 123
@pytest.mark.asyncio
async def test_cancelling_execution_drains_the_blocking_engine_thread(monkeypatch):
started = threading.Event()