Enhanced upload API
Endpoint description
Enhanced upload submits a local audio file; the system performs the enhancement in the background and produces a complete, playable song. The submit call returns the task information immediately, and the client polls the query endpoint for progress.
Submit endpoint: POST /api/music/enhanced-upload
Single-task query: GET /api/music/enhanced-upload/:id
Cancel a task: POST /api/music/enhanced-upload/:id/cancel
List query: GET /api/music/enhanced-upload
Billing: 10 ¥ per call, pre-charged at the fixed suno-enhanced-upload price. When a task fails, or is cancelled during the allowed stage, the pre-charged amount is refunded automatically. The amount actually charged follows the current back-office price configuration.
Call flow
- Call
POST /api/music/enhanced-uploadto upload the audio file. - Save the returned
task_id. - Call
GET /api/music/enhanced-upload/:idto check progress and results. - Once Suno has finished rendering, the service uses the Suno account bound to that task to call the Studio authorised-download endpoint and writes the MP3 into the CN2 media service.
- The task becomes
completedonly after the CN2 asset is ready; at that point read the CDN audio address fromaudio_urlin the response.
/api/forbidden is a placeholder address that can appear in Suno Studio metadata; it is not a playable or downloadable resource. It is never returned to customers and is not used as proof of completion. If rendering has finished but CN2 is still preparing, the endpoint keeps returning processing and does not return audio_url; the client should keep polling and must not treat the empty address as a failure.
Submit an enhanced upload
Headers
| Parameter | Type | Required | Notes |
|---|---|---|---|
| Authorization | string | yes | Bearer YOUR_API_KEY |
| Content-Type | string | no | Do not set it manually for multipart requests; let the client generate it |
Form parameters
| Parameter | Type | Required | Default | Notes |
|---|---|---|---|---|
| file | file | yes | - | Local audio file, maximum 80 MB |
| title | string | no | file name without its extension | Song title |
Request example
The example below uses the same call as in production validation, but the API key has been replaced with a placeholder.
curl.exe --http1.1 -s -S \
-H "Authorization: Bearer YOUR_API_KEY" \
-F "file=@source.aac" \
-F "title=Enhanced upload demo" \
"https://www.suno-api.io/api/music/enhanced-upload"
Response
{
"success": true,
"message": "",
"data": {
"task_id": 3209,
"song_id": "pending:enhanced-upload:cu_20260611003241723483700xnCcQg",
"client_request_id": "cu_20260611003241723483700xnCcQg",
"title": "Enhanced upload demo",
"file_name": "source.aac",
"status": "queued",
"created_at": 1781137961,
"pre_consumed_quota": 5000000,
"billing_source": "wallet"
}
}
Query a single task
Request example
curl.exe --http1.1 -s -S \
-H "Authorization: Bearer YOUR_API_KEY" \
"https://www.suno-api.io/api/music/enhanced-upload/3209"
Processing response example
{
"success": true,
"message": "",
"data": {
"task": {
"task_id": 3209,
"song_id": "pending:enhanced-upload:cu_20260611003241723483700xnCcQg",
"client_request_id": "cu_20260611003241723483700xnCcQg",
"title": "Enhanced upload demo",
"file_name": "source.aac",
"status": "processing",
"type": "enhanced_upload",
"progress": {
"stage": "media_preparing",
"percent": 98,
"label": "正在准备播放资源",
"updated_at": 1781138500
},
"pre_consumed_quota": 5000000,
"billing_source": "wallet",
"created_at": 1781137961,
"updated_at": 1781138500
}
}
}
Completed response example
{
"success": true,
"message": "",
"data": {
"task": {
"task_id": 3209,
"song_id": "56cbd0bb-0e8c-4a34-8729-55d5c05d9c53",
"client_request_id": "cu_20260611003241723483700xnCcQg",
"title": "Enhanced upload demo",
"file_name": "source.aac",
"status": "completed",
"type": "enhanced_upload",
"audio_url": "https://media.code-go.com/assets/56cbd0bb-0e8c-4a34-8729-55d5c05d9c53-mp3.mp3",
"duration": 217.74,
"progress": {
"stage": "completed",
"percent": 100,
"label": "已完成",
"updated_at": 1781138943
},
"pre_consumed_quota": 5000000,
"billing_source": "wallet",
"created_at": 1781137961,
"updated_at": 1781138943,
"completed_at": 1781138943
}
}
}
Cancel a task
A task can be cancelled only while both the task and the back-end workflow are still in the queued stage. Once the task enters leasing, running, processing, or has completed, it cannot be cancelled.
Request example
curl.exe --http1.1 -s -S -X POST \
-H "Authorization: Bearer YOUR_API_KEY" \
"https://www.suno-api.io/api/music/enhanced-upload/3209/cancel"
Response
{
"success": true,
"message": "",
"data": {
"task_id": 3209,
"song_id": "pending:enhanced-upload:cu_20260611003241723483700xnCcQg",
"client_request_id": "cu_20260611003241723483700xnCcQg",
"status": "cancelled"
}
}
If the task has already started processing, the endpoint returns:
{
"success": false,
"message": "强化上传已开始处理,无法取消"
}
Query the task list
The list endpoint returns only the enhanced upload tasks of the user the current API key belongs to; ordinary generation, cover and extend tasks are not mixed in.
Query parameters
| Parameter | Type | Required | Default | Notes |
|---|---|---|---|---|
| p | number | no | 1 | Page number |
| page_size | number | no | system default | Items per page, maximum 100 |
Request example
curl.exe --http1.1 -s -S \
-H "Authorization: Bearer YOUR_API_KEY" \
"https://www.suno-api.io/api/music/enhanced-upload?p=1&page_size=3"
Response
{
"success": true,
"message": "",
"data": {
"page": 1,
"page_size": 3,
"total": 1,
"items": [
{
"task_id": 3209,
"song_id": "56cbd0bb-0e8c-4a34-8729-55d5c05d9c53",
"client_request_id": "cu_20260611003241723483700xnCcQg",
"title": "Enhanced upload demo",
"file_name": "source.aac",
"status": "completed",
"type": "enhanced_upload",
"audio_url": "https://media.code-go.com/assets/56cbd0bb-0e8c-4a34-8729-55d5c05d9c53-mp3.mp3",
"duration": 217.74,
"progress": {
"stage": "completed",
"percent": 100,
"label": "已完成",
"updated_at": 1781138943
},
"pre_consumed_quota": 5000000,
"billing_source": "wallet",
"created_at": 1781137961,
"updated_at": 1781138943,
"completed_at": 1781138943
}
]
}
}
Response field reference
| Field | Type | Notes |
|---|---|---|
| task_id | number | Enhanced upload task ID; use this value for later queries and cancellation |
| song_id | string | pending:enhanced-upload:* while processing; the real song ID once completed |
| client_request_id | string | Client request tracking ID |
| status | string | Task status, such as queued, processing, completed, failed, cancelled |
| type | string | Always enhanced_upload |
| audio_url | string | Audio address once completed |
| duration | number | Audio duration in seconds |
| progress.stage | string | Current processing stage |
| progress.percent | number | Progress percentage |
| progress.label | string | Progress text shown to the user |
| pre_consumed_quota | number | Quota pre-charged for this call |
| billing_source | string | Billing source, such as wallet |
| error_message | string | Failure reason |
Notes
- This endpoint currently supports multipart file upload only; JSON
file_urlandfile_base64are not supported. - The uploaded file is at most 80 MB.
- The submit endpoint is asynchronous: a
queuedresponse means the task has been enqueued, not that the audio is finished. - Cancellation only applies to tasks that have not started processing; once processing begins the platform account workflow is not interrupted.
- Do not expose real API keys in client-side code.
Start a cover after the enhanced upload completes
Once the enhanced upload is complete, you can use the finished result as the source clip and call POST /api/music/generate-from-source to start a cover.
Note: a cover is a synchronous endpoint — an order is only accepted when the response arrives, and measured cases can take up to about 230 seconds. Set your client timeout to 300 seconds or more, and do not retry immediately after a timeout. See "Wait times and timeout settings" in the New API overview.
First poll GET /api/music/enhanced-upload/:id until task.status is completed. At that point:
task.song_idis the real song ID and is thesourceClipIdthe cover endpoint needs;task.audio_urlis best passed along assourceAudioUrl, so the server can handle the case where the source clip and the executing account differ;task.task_idis only the enhanced upload task ID and cannot be used assourceClipId;pending:enhanced-upload:*is a placeholder ID for the processing stage and cannot be used for a cover.
When starting the cover, use the same API key as for the enhanced upload and assemble the request according to the field mapping below:
| Cover request field | Where the value comes from |
|---|---|
sourceClipId |
task.song_id from the completed enhanced upload |
sourceAudioUrl |
task.audio_url from the completed enhanced upload |
sourceTitle |
task.title from the completed enhanced upload |
Fill in the remaining lyrics, style, title and model parameters according to the cover from a source clip API. Once the cover endpoint returns the new clips[].song_id, use POST /api/music/query to check the generation status and the final audio.
Get an API key
Create an API key in the console after signing up. ¥0.6 per run returns 2 tracks, downloads are unlimited, and no phone number is required.
Get API key Back to overview