Fix clone API: drop no-op instruct, serialize generation, clearer errors

- Remove the 'instruct' style field: Qwen3-TTS Base generate_voice_clone
  silently ignores it, so the UI option did nothing.
- Serialize generations with a lock so concurrent requests queue instead
  of doubling RAM/VRAM on one shared model.
- Validate empty text/ref_text ourselves so the API returns the Korean
  400 messages instead of FastAPI's generic 422.
- UI: explain that mic recording needs https/localhost instead of a raw
  TypeError on plain-http LAN access.
- README: document mic/https limit, queueing, and measured CPU speed.

Verified on CPU (Python 3.12, torch 2.14 CPU, 0.6B Base): wav and mp3
references, language ko/auto, two concurrent requests -> all 200 and
Whisper transcripts match the requested text.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
voice_copy bot
2026-10-05 04:11:39 +09:00
parent 1b691b071b
commit a34f16123f
4 changed files with 32 additions and 28 deletions

View File

@@ -66,10 +66,6 @@
<label>언어</label>
<select id="language"></select>
</div>
<div>
<label>스타일 지시 <span class="hint">(선택)</span></label>
<input type="text" id="instruct" placeholder="예) 밝고 활기차게" />
</div>
<div>
<label>seed <span class="hint">(선택)</span></label>
<input type="number" id="seed" placeholder="랜덤" />
@@ -119,6 +115,10 @@ $("file").addEventListener("change", () => {
// ── Mic recording → in-browser WAV (no ffmpeg needed) ──
$("recBtn").addEventListener("click", async () => {
if (!window.isSecureContext || !navigator.mediaDevices) {
setStatus("브라우저 보안 정책상 마이크 녹음은 https 또는 localhost 접속에서만 됩니다. 녹음 파일을 업로드해 주세요.", "err");
return;
}
try {
stream = await navigator.mediaDevices.getUserMedia({ audio: true });
} catch (e) { setStatus("마이크 접근 실패: " + e.message, "err"); return; }
@@ -179,7 +179,6 @@ $("go").addEventListener("click", async () => {
fd.append("ref_text", refText);
fd.append("text", text);
fd.append("language", $("language").value);
fd.append("instruct", $("instruct").value.trim());
fd.append("seed", $("seed").value.trim());
$("go").disabled = true;