---
title: "Synthesize text in a cloned voice"
method: POST
path: "/api/v1/clone"
tags: ["Public API v1"]
---

# Synthesize text in a cloned voice

`POST /api/v1/clone`

Zero-shot voice cloning. Upload a reference clip via POST /v1/upload, then pass its `refFileId` plus the exact `refText` (transcript of that clip) to synthesize `text` in that voice. Pass `engine` ("v3" default, "v4" premium) to choose the cloning engine; billing carries that engine's multiplier. Tokens are deducted upfront from `text`. Returns a presigned `audioUrl`.

## Request body

- PublicCloneRequestDto
  - `text` string, required — Vietnamese text to synthesize in the cloned voice.
  - `refFileId` string, required — fileId returned by POST /v1/upload — the reference audio to clone. Must be one of your own uploads.
  - `refText` string, required — Exact transcript of the reference audio. Required for zero-shot cloning quality.
  - `emotion` 'natural' | 'storytelling' | 'tin_tuc' | 'tu_nhien' | 'doc_truyen' | 'emotion_0' | 'emotion_1' | 'emotion_2' | 'emotion_3' | 'emotion_4' | 'emotion_5' | 'emotion_6' | 'emotion_7' | 'emotion_8' | 'emotion_9' | 'emotion_10' | 'emotion_11' | 'emotion_12' | 'emotion_13' | 'emotion_14' | 'emotion_15' | 'emotion_16' | 'emotion_17' | 'emotion_18' | 'emotion_19'
  - `temperature` number
  - `aiRefine` boolean — AI text refinement. Defaults to FALSE on the public API: the text is synthesized as submitted, with no AI moderation and no pronunciation normalization, billed at the plain per-character rate. Set true to run the same AI step the web app uses — formulas, acronyms and mixed-in English are read correctly and the content is checked — billed with the AI surcharge and one extra model round-trip of latency. Deterministic text preparation is applied either way.
  - `engine` 'v3' | 'v4' — TTS engine to clone on — "v3" (default) or "v4" (premium, billed at its own multiplier; V4 is built for cloning). The engine must declare the "clone" capability. Omit to use the platform default.

## Response `201`

The synthesized audio in the cloned voice, as a presigned URL.

- PublicCloneResponseDto
  - `success` boolean, required
  - `audioUrl` string, required — Presigned S3 download URL for the cloned-voice WAV.
  - `audioUrlExpiresIn` number, required — Seconds until audioUrl expires.
  - `duration` number, required — Duration of the synthesized audio (seconds).
  - `tokenCost` number, required — Tokens deducted for this request.

## Other responses

- `400` — Unknown `refFileId`, a reference clip outside the engine’s duration window, or a `refText` that does not match the clip.
- `401` — API key missing, malformed, or revoked.
- `403` — Your plan does not include cloning or this engine, or the grant is out of tokens / expired.
- `422` — Content refused by moderation. Only reachable with `aiRefine: true`.
- `429` — Rate limit or token quota exceeded. When the limit came from the application the response carries `Retry-After` (seconds) and the `X-RateLimit-*` headers and is counted against your API key; a 429 with none of those headers came from the edge proxy and is counted against your source address, shared with every other key calling from it. Back off on either.

---

[API](https://skmtc.dev/vieneu/apis/vieneu-api.md) · [All operations](https://skmtc.dev/vieneu/apis/vieneu-api/llms.txt) · [OpenAPI document](https://skmtc-service-production.skmtc.workers.dev/v1/apis/vieneu/vieneu-api/revisions/11c8166a6c4d/schema)
