Heavo AI

exclusive
https://back.gard-api.org/api/v1/heavo-ai

Heavo AI is Gard’s white-label music stack: create a project, start generation (sync or async with task polling), poll GET /tracks/{track_id}/status for each track id from the task, extend, WAV/MP3 download, webhooks on credits-backed SLAs — all under /api/v1/heavo-ai. Listing all projects or all tracks in a project is not part of the public contract.

Authentication

Every request to Gard API requires the X-API-Key header. Create keys in the API Keys section of your dashboard.

Base URL
https://back.gard-api.org
curl -X POST "https://back.gard-api.org/api/v1/heavo-ai/projects?title=Demo%20project" \
  -H "X-API-Key: gard_live_..."

Endpoints

GET: query parameters as one object (no JSON body on the wire). Multipart routes: logical fields — send as form-data, values shown as JSON for clarity.

POST
/api/v1/heavo-ai/projects

Create an empty project. The display name is sent as query parameter title (default Untitled Project). Response id is your Heavo project UUID — store it for POST /generate and GET /projects/{project_id}.

Request body
FieldTypeRequiredDescription
titlestringnoQuery string (not JSON body). Display name.
Example request (JSON)
POST /api/v1/heavo-ai/projects?title=My%20EP
(no JSON body — only query string)
Example response (JSON)
{
  "id": "8f2c…-uuid…",
  "title": "My EP",
  "created_at": "2026-04-29T12:00:00+00:00"
}
GET
/api/v1/heavo-ai/projects/{project_id}

Get one project metadata (merged with upstream when available).

Example response (JSON)
{ "id": "…", "title": "…", "created_at": "…" }
GET
/api/v1/heavo-ai/censored-style-tags

List opaque gst_<hex> style-tag ids for censor/censored: true advanced tags (and optional extend tags). Server maps these ids to internal Heavo catalogue strings; raw catalogue wording is not exposed. Response shape: { code, msg, data: { meta, tags } }.

Example request (JSON)
GET /api/v1/heavo-ai/censored-style-tags
Example response (JSON)
{
  "code": 200,
  "msg": "success",
  "data": {
    "meta": { "version": 1, "generated_from": "censored_allowed_tags.txt", "count": 4160, "gard_tag_prefix": "gst_" },
    "tags": [
      { "gard_tag_id": "gst_7f2a4b8c…", "ordinal": 0 }
    ]
  }
}
POST
/api/v1/heavo-ai/generate

Start track generation. Query: project_id (UUID, required) and optional sync (false default). Body matches GenerateRequest. censor or censored (bool) is required — either JSON key is accepted. generation_mode: simple (default) or advanced (alias JSON key mode). Implied advanced when tags is non-empty. Simple: non-empty prompt only — must not send tags or lyrics. Advanced: non-empty tags; optional lyrics and prompt. With censor/censored: true, advanced tags must be gst_… ids from GET /censored-style-tags; free-form tokens that resolve to artist catalogue rows return 400 with In censored mode, generation in the style of artists is not available.; style catalogue hits use a separate gst-only message; unknown tokens use a generic gst-prefix error. model: V1 or V1_PLUS (upstream quality tier; V1_PLUS may return multiple track_ids per task). Omitting censor/censored422 validation error. A unique cover art image is generated by Heavo AI for each generation and delivered in the cover_art field of the task and webhook payloads.

Request body
FieldTypeRequiredDescription
project_idUUIDyesQuery parameter — Heavo project id.
syncbooleannoQuery. If false (default): async — data.taskId in JSON envelope.
censor / censoredbooleanyesEither field name. Censorship + gst-only tag policy when true.
generation_modestringnoAlias mode. With non-empty tags, mode is treated as advanced.
Options: simple · advanced
promptstringnoSimple: required text. Advanced: optional when tags carry style (may be empty).
tagsstring[]noAdvanced only — non-empty array. Uncensored: normalized via suggest cache. Censored: gst_… only.
lyricsstringnoAdvanced optional lyric line; censored: artist names blocked.
instrumentalbooleannoNo vocals when true.
prompt_strengthnumberno0–2
style_scalenumberno0–3
titlestringnoOptional — updates composition title when set.
modelstringnoV1 — standard tier. V1_PLUS — enhanced upstream tier (may yield multiple track_ids from one generation).
Options: V1 · V1_PLUS
callback_urlurlnoHTTPS webhook for track_ready when finished.
Example request (JSON)
Query: ?project_id=<uuid>&sync=false

// Simple + async — no tags/lyrics
{
  "censor": false,
  "generation_mode": "simple",
  "prompt": "melodic techno 128bpm wide pads",
  "model": "V1",
  "instrumental": false,
  "prompt_strength": 1.0,
  "style_scale": 2.0,
  "callback_url": null
}

// Advanced + uncensored — free-form tags (and optional lyrics)
{
  "censored": false,
  "generation_mode": "advanced",
  "prompt": "",
  "tags": ["techno", "analog drums"],
  "lyrics": "optional line",
  "model": "V1_PLUS",
  "instrumental": false,
  "prompt_strength": 1.0,
  "style_scale": 2.0
}

// Advanced + censored — only gst_ ids from GET /censored-style-tags
{
  "censor": true,
  "mode": "advanced",
  "prompt": "",
  "tags": ["gst_7f2a4b8c…"],
  "model": "V1",
  "instrumental": false,
  "prompt_strength": 1.0,
  "style_scale": 2.0
}
Example response (JSON)
// async (sync=false) — immediate envelope
{
  "code": 200,
  "msg": "success",
  "data": {
    "taskId": "a1b2c3d4e5f678901234567890ab12cd"
  }
}

// sync (sync=true) — returns public track_ids when upstream finishes
{
  "success": true,
  "track_ids": ["…"],
  "project_id": "<uuid>",
  "webhook_job_id": 42
}
422 if censor / censored is missing. 400 censorship examples: artist reference in simple prompt; non-gst tags when censored (wording varies: artist catalogue hit vs style-only vs generic). Credits: censor/censored: true → 5 · false → 8 (async path charges when the task is enqueued). Refunded on upstream failure.
GET
/api/v1/heavo-ai/generation-tasks/{taskId}

Poll async generation using the taskId from POST /generate (data.taskId) as the path segment. status moves queuedprocessingsucceeded | failed. When succeeded, track_ids lists Gard public track ids — poll GET /tracks/{track_id}/status for each id for streaming URLs and READY state. Includes censor (bool) echoing the original generate request. cover_art contains the HTTPS URL of the AI-generated cover art image (shared by all tracks in this generation) once ready.

Example response (JSON)
{
  "task_id": "a1b2c3d4e5f678901234567890ab12cd",
  "status": "succeeded",
  "phase": null,
  "project_id": "<uuid>",
  "track_ids": ["pub_…", "pub_…"],
  "cover_art": "https://trust.gard-api.org/cover_art/a1b2c3d4.png",
  "censor": false,
  "error": null,
  "webhook_job_id": 12
}
GET
/api/v1/heavo-ai/tracks/{track_id}/status

Poll single-track generation / processing state (PROCESSING, STREAMING_READY, READY, etc.). Prefer this for player UX during render. When known, censor echoes the censorship flag from the generate/extend that created this track. cover_art contains the generated cover art URL when available. Streaming vs Final: When status is STREAMING_READY, song_url contains a streaming URL (on back.gard-api.org) suitable for immediate playback while the track is still rendering. The stream_song_url field also holds this URL. Once status transitions to READY, song_url updates to the final CDN file (on trust.gard-api.org) and stream_song_url becomes null. Clients should use stream_song_url ?? song_url for playback and treat song_url at READY status as the definitive download/final URL.

Example response (JSON)
{
  "id": "<public_track_uuid>",
  "status": "STREAMING_READY",
  "song_url": "https://back.gard-api.org/api/v1/heavo-ai/stream/<uuid>",
  "stream_song_url": "https://back.gard-api.org/api/v1/heavo-ai/stream/<uuid>",
  "cover_art": "https://trust.gard-api.org/cover_art/a1b2c3d4.png",
  "title": "Track Title",
  "duration": 174,
  "censor": false
}

// When READY (final):
{
  "id": "<public_track_uuid>",
  "status": "READY",
  "song_url": "https://trust.gard-api.org/generations3/audio_<uuid>.ogg",
  "stream_song_url": null,
  "cover_art": "https://trust.gard-api.org/cover_art/a1b2c3d4.png",
  "title": "Track Title",
  "duration": 174,
  "censor": false
}
POST
/api/v1/heavo-ai/extend

Extend or branch a track inside a project (continuation / extra section). Body includes project_id, track_id (Heavo id), timing (side, context_seconds, crop_duration), censor/censored (required bool), optional prompt and tags, model, optional callback_url (extend_ready). When censor/censored is true, any non-empty tags entries must be gst_… from GET /censored-style-tags; artist wording in prompt is blocked. Validation matches generate censorship rules (no separate V1 vs V1_PLUS branch).

Request body
FieldTypeRequiredDescription
project_idUUIDyesHeavo project.
track_idstringyesSource Heavo track id.
censor / censoredbooleanyesEither JSON key. Required since schema update.
sidestringnoleft or right (extend direction).
context_secondsnumbernoContext window.
crop_durationnumbernoSource crop length.
promptstringnoContinuation hint; censored: artist names blocked.
tagsstring[]noOptional. Censored: gst_… only when non-empty.
modelstringnoSame resolution as generate.
Options: V1 · V1_PLUS
callback_urlurlnoWebhook when extension is ready.
Example request (JSON)
{
  "track_id": "…",
  "project_id": "<uuid>",
  "censor": true,
  "side": "right",
  "context_seconds": 122.6,
  "crop_duration": 69.4,
  "prompt": "keep energy, add breakbeat",
  "tags": [],
  "model": "V1"
}
Example response (JSON)
{
  "success": true,
  "track_ids": ["…"],
  "project_id": "<uuid>",
  "webhook_job_id": null
}
4.5 credits on success; refunded on upstream failure.
POST
/api/v1/heavo-ai/download-audio

Request a mp3 or wav download URL for a Heavo track_id. Optional callback_url (audio_download_ready). No credit charge.

Request body
FieldTypeRequiredDescription
track_idstringyesHeavo track id.
formatstringnomp3 or wav.
callback_urlurlnoOptional webhook.
Example request (JSON)
{ "track_id": "…", "format": "mp3" }
Example response (JSON)
{ "audio_url": "https://…", "webhook_job_id": null }
GET
/api/v1/heavo-ai/webhooks

List your webhook delivery jobs (optional status, limit).

Example response (JSON)
{ "data": [ { "id": 1, "event": "track_ready", "status": "DELIVERED", … } ] }
GET
/api/v1/heavo-ai/webhooks/{job_id}

Inspect one webhook job: attempts, last error, delivered_at.

Example response (JSON)
{ "id": 12, "event": "track_ready", "status": "PENDING", "callback_url": "…", … }

Callback (webhook)

Whenever an endpoint accepts callback_url, Gard POSTs a signed JSON payload to your URL when work finishes. Retries use exponential backoff (up to 24h).

Heavo AI uses the shared Gard webhook transport. Typical event values you will see include track_ready, extend_ready, video_ready, and audio_download_ready — depending on which endpoint queued the job. Payload shapes mirror the synchronous JSON you would get from polling. For jobs started with async POST /generate (sync=false), callbacks include taskId — the same id returned in data.taskId.

POST https://your-app.com/webhook
X-Gard-Signature: sha256=...
Content-Type: application/json

{
  "event": "track_ready",
  "job_id": 42,
  "timestamp": "2026-04-29T12:34:56+00:00",
  "success": true,
  "taskId": "a1b2c3d4e5f678901234567890ab12cd",
  "project_id": "<heavo_project_uuid>",
  "tracks": [
    { "id": "<heavo_track_uuid>", "status": "STREAMING_READY", "song_url": "https://…" }
  ]
}