Generate a song

June 3, 2026

Table of contents

  1. Request Headers
  2. Request Body
  3. Responses
  4. Model
  5. Examples
  6. Try It

Generate a complete song from a text prompt using Lyria 3 Pro. Whether the result is vocal or instrumental is decided by the model from your prompt β€” describe vocals (or pass your own lyrics) to get a sung track with model-written lyrics, or set instrumental: true to force an instrumental. Each generation returns up to two clips (an A/B pair) and consumes credits from your account balance.

https://api.useapi.net/v1/flowmusic/music

Request Headers

Authorization: Bearer {API token}
Content-Type: application/json
# Alternatively you can use multipart/form-data
# Content-Type: multipart/form-data

Request Body

{
  "prompt": "lo-fi hip hop, mellow piano, 80 bpm",
  "instrumental": false,
  "ghostwriter": "pro"
}
  • email is optional. The Flow Music account to use. See GET /accounts for configured accounts. If not provided, the API automatically selects an account with available capacity. Specify when you want to use a specific configured account.
  • prompt is required, the song description β€” style, mood, genre, instruments, BPM, and any vocal direction. 1–10,000 characters.
  • instrumental is optional. true forces an instrumental (prepends an [Instrumental] tag). false (default) lets the model decide whether to sing based on your prompt.
  • lyrics is optional, your own lyrics, ideally [Verse]/[Chorus]-tagged (≀10,000 chars). Providing them forces a vocal render of those words. Omit them and the model writes lyrics only if the prompt implies vocals.
  • ghostwriter is optional, the lyrics-writer version used when the model writes the lyrics. It has no effect if you supply your own lyrics. Supported values: standard, pro.
  • refImage1 to refImage10 are optional, encoded image asset IDs from POST /files or POST /files/generate. Passed to the model only as uploaded-file hints (it may loosely nudge style) β€” not a literal reference.
  • refAudio1 to refAudio10 are optional, encoded audio asset IDs from POST /files. Experimental, limited effect β€” the current Lyria 3 Pro model does not truly reference an uploaded song. The upload is passed only as a hint and may not influence the result.
  • mode is optional, sync (default β€” the request blocks until the song is ready, ~40–150 s) or async (returns 201 immediately with a jobid). Poll GET /jobs/jobid for completion.
  • replyUrl is optional, webhook URL. When the job completes or fails the API POSTs the job record to it β€” the same shape as GET /jobs/jobid.
  • replyRef is optional, custom reference string echoed back in the webhook.

References must come from one account. A refImage/refAudio ID is tied to the account it was uploaded to. If you pass any references, they must all be from the same account, and the song is generated on that account. If you also pass email, it must be that same account β€” otherwise the request fails with 400.

Responses

  • 200 OK

    Sync mode (default, or "mode": "sync") β€” the song is generated and the full record is returned inline. All audio lives in the clips[] array.

    {
      "jobid": "job:aaaabbbb-cccc-4ddd-8eee-ffff99990000-user:[email protected]:flowmusic",
      "email": "[email protected]",
      "status": "completed",
      "created_at": "2026-06-01T18:40:42.412Z",
      "completed_at": "2026-06-01T18:42:55.123Z",
      "duration_ms": 132711,
      "clips": [
        {
          "clip": "user:[email protected]:a1b2c3d4-e5f6-4a7b-8c9d-0e1f2a3b4c5d",
          "title": "Morning Sun",
          "duration_s": 173.04,
          "lyrics": "[Verse 1]\nCity lights blur in the rain\n[Chorus]\nAnd I will wait for the morning sun",
          "seed": null,
          "lyrics_timing": [ [0.0, 2.4], [2.4, 5.1] ],
          "created_at": "2026-06-01T18:41:04.283Z",
          "audio_url": "https://storage.googleapis.com/...a1b2c3d4.m4a",
          "wav_url": "https://storage.googleapis.com/...a1b2c3d4.wav",
          "image_url": "https://storage.googleapis.com/...b2c3d4e5.jpg"
        }
      ],
      "request": { "prompt": "lo-fi hip hop, mellow piano, 80 bpm", "instrumental": false }
    }
    
  • 201 Created

    Async mode ("mode": "async") β€” the job is queued and returned immediately as pending. Poll GET /jobs/jobid until status is completed or failed.

    {
      "jobid": "job:aaaabbbb-cccc-4ddd-8eee-ffff99990000-user:[email protected]:flowmusic",
      "email": "[email protected]",
      "status": "pending",
      "created_at": "2026-06-01T18:40:42.412Z",
      "request": {
        "prompt": "upbeat funk groove, 110 bpm",
        "instrumental": true,
        "mode": "async"
      }
    }
    
  • 400 Bad Request

    Validation error (missing/invalid parameter, or no account configured).

    {
      "error": "Parameter prompt is required",
      "code": 400
    }
    
  • 401 Unauthorized

    Invalid API token.

    {
      "error": "Unauthorized",
      "code": 401
    }
    
  • 422

    The model produced no audio (e.g. a content-moderation refusal). A terminal job record with status: "failed".

    {
      "jobid": "job:aaaabbbb-cccc-4ddd-8eee-ffff99990000-user:[email protected]:flowmusic",
      "email": "[email protected]",
      "status": "failed",
      "created_at": "2026-06-01T18:40:42.412Z",
      "completed_at": "2026-06-01T18:41:10.512Z",
      "error": {
        "code": "moderation_reject",
        "message": "the model declined to generate audio for this prompt"
      },
      "request": { "prompt": "...", "instrumental": false }
    }
    
  • 429 Too Many Requests

    Returned in two cases.

    email omitted and every configured account is already at its maxJobs concurrency limit (load-balancing has nowhere to place the job) β€” retry once a running job finishes:

    {
      "error": "All 3 FlowMusic accounts are at their maxJobs concurrency limit β€” retry shortly",
      "code": 429
    }
    

    Or passed through from FlowMusic when a chosen account exceeds its own per-account limit (a single or email-targeted account running too many generations at once):

    {
      "error": "FlowMusic conversation failed (429): {\"detail\":\"Too Many Requests\"}",
      "code": 429
    }
    
  • 596 Account Error

    The account targeted by email is in an error state and can’t be used β€” re-add it via POST /accounts. The error field returns whatever reason was recorded for the account.

    {
      "error": "Account [email protected] in error state: refresh token rejected",
      "code": 596
    }
    

Model

  • {
      jobid: string                  // job:<uuid>-user:<id>-<email>-bot:flowmusic
      email: string
      status: 'completed' | 'pending' | 'failed'
      created_at: string             // ISO 8601 timestamp
      completed_at?: string          // present when terminal
      duration_ms?: number           // wall-clock generation time
      clips: Array<{
        clip: string                 // encoded clip asset id β€” use with /music/download and /music/edit
        title: string | null
        duration_s: number | null
        lyrics: string | null        // [Verse]/[Chorus]-tagged; "[Instrumental]" for instrumentals
        seed: number | null
        lyrics_timing: Array<[number, number]> | null  // timing markers, [start, end] seconds (vocal clips)
        created_at: string           // ISO 8601 timestamp
        audio_url: string            // signed m4a download URL
        wav_url: string              // signed wav download URL
        image_url: string | null     // auto-generated artwork URL
      }>
      request: {                     // the request body you submitted, echoed back verbatim
        prompt: string
        email?: string
        instrumental?: boolean
        lyrics?: string
        ghostwriter?: 'standard' | 'pro'
        mode?: 'sync' | 'async'
        replyUrl?: string
        replyRef?: string
        refImage1?: string           // …up to refImage10 β€” encoded image asset IDs
        refAudio1?: string           // …up to refAudio10 β€” encoded audio asset IDs
      }
    }
    
  • {
      jobid: string                  // job:<uuid>-user:<id>-<email>-bot:flowmusic
      email: string
      status: 'pending'
      created_at: string             // ISO 8601 timestamp
      request: {                     // the request body you submitted, echoed back verbatim
        prompt: string
        email?: string
        instrumental?: boolean
        lyrics?: string
        ghostwriter?: 'standard' | 'pro'
        mode?: 'sync' | 'async'
        replyUrl?: string
        replyRef?: string
        refImage1?: string           // …up to refImage10 β€” encoded image asset IDs
        refAudio1?: string           // …up to refAudio10 β€” encoded audio asset IDs
      }
    }
    

Examples

  • curl -H "Content-Type: application/json" \
         -H "Authorization: Bearer YOUR_API_TOKEN" \
         -X POST "https://api.useapi.net/v1/flowmusic/music" \
         -d '{ "prompt": "lo-fi hip hop, mellow piano, 80 bpm" }'
    
  • const response = await fetch('https://api.useapi.net/v1/flowmusic/music', {
      method: 'POST',
      headers: {
        'Authorization': 'Bearer YOUR_API_TOKEN',
        'Content-Type': 'application/json'
      },
      body: JSON.stringify({
        prompt: 'lo-fi hip hop, mellow piano, 80 bpm'
      })
    });
    const result = await response.json();
    console.log(result.clips?.[0]?.audio_url);
    
  • import requests
    
    response = requests.post(
        'https://api.useapi.net/v1/flowmusic/music',
        headers={'Authorization': 'Bearer YOUR_API_TOKEN'},
        json={'prompt': 'lo-fi hip hop, mellow piano, 80 bpm'}
    )
    print(response.status_code, response.json())
    

Try It