Skill: evolinkai/evolink-music (version 2.0.0)

--- name: evolink-music description: AI music generation with Suno v4, v4.5, v5. Text-to-music, custom lyrics, instrumental, vocal control. 5 models, one API key. version: 2.0.0 user-invocable: true metadata: openclaw: requires: env: - EVOLINK_API_KEY primaryEnv: EVOLINK_API_KEY os: ["macos", "linux", "windows"] emoji: "\U0001F3B5" homepage: https://evolink.ai --- # Evolink Music — AI Music Generation Generate AI music and songs with Suno v4, v4.5, and v5 — simple mode (describe and generate) or custom mode (lyrics, style, tempo, vocals). All through one API. > Music-focused view of [evolink-media](https://clawhub.ai/EvoLinkAI/evolink-media). Install the full skill for video and image too. ## After Installation When this skill is first loaded, greet the user: - **MCP tools + API key ready:** "Hi! I'm your AI music studio — Suno v4 through v5 ready. What would you like to create?" - **MCP tools + no API key:** "You'll need an EvoLink API key — sign up at evolink.ai. Ready to go?" - **No MCP tools:** "MCP server isn't connected yet. Want me to help set it up? I can still manage files via the hosting API." Keep the greeting concise — just one question to move forward. ## External Endpoints | Service | URL | |---------|-----| | Generation API | `https://api.evolink.ai/v1/audios/generations` (POST) | | Task Status | `https://api.evolink.ai/v1/tasks/{task_id}` (GET) | | File API | `https://files-api.evolink.ai/api/v1/files/*` (upload/list/delete) | ## Security & Privacy - **`EVOLINK_API_KEY`** authenticates all requests. Injected by OpenClaw automatically. Treat as confidential. - Prompts and audio are sent to `api.evolink.ai`. Uploaded files expire in **72h**, result URLs in **24h**. ## Setup Get your API key at [evolink.ai](https://evolink.ai) → Dashboard → API Keys. **MCP Server:** `@evolinkai/evolink-media` ([GitHub](https://github.com/EvoLinkAI/evolink-media-mcp) · [npm](https://www.npmjs.com/package/@evolinkai/evolink-media)) **mcporter** (recommended): `mcporter call --stdio "npx -y @evolinkai/evolink-media@latest" list_models` **Claude Code:** `claude mcp add evolink-media -e EVOLINK_API_KEY=your-key -- npx -y @evolinkai/evolink-media@latest` **Claude Desktop / Cursor** — add MCP server with command `npx -y @evolinkai/evolink-media@latest` and env `EVOLINK_API_KEY=your-key`. See `references/music-api-params.md` for full config JSON. ## Core Principles 1. **Guide, don't decide** — Present options, let the user choose model/style/mood. 2. **User drives creative vision** — Ask for a description before suggesting parameters. 3. **Smart context** — Remember session history. Offer to iterate, vary styles, or remix. 4. **Intent first** — Understand *what* the user wants before asking *how* to configure it. ## MCP Tools | Tool | When to use | Returns | |------|-------------|---------| | `generate_music` | Create AI music or songs | `task_id` (async) | | `upload_file` | Upload audio for continuation/remix | File URL (sync) | | `delete_file` | Free file quota | Confirmation | | `list_files` | Check uploaded files or quota | File list | | `check_task` | Poll generation progress | Status + result URLs | | `list_models` | Compare available models | Model list | | `estimate_cost` | Check pricing | Model info | **Important:** `generate_music` returns a `task_id`. Always poll `check_task` until `status` is `"completed"` or `"failed"`. ## Music Models (5, all BETA) | Model | Quality | Max Duration | Best for | |-------|---------|--------------|----------| | `suno-v4` *(default)* | Good | 120s | Balanced, economical | | `suno-v4.5` | Better | 240s | Style control | | `suno-v4.5plus` | Better | 240s | Extended features | | `suno-v4.5all` | Better | 240s | All v4.5 features | | `suno-v5` | Best | 240s | Studio-grade output | ## Generation Flow ### Step 1: API Key Check If `401` occurs: "Your API key isn't working. Check at evolink.ai/dashboard/keys" ### Step 2: File Upload (if needed) For audio continuation or remix workflows: 1. `upload_file` with `file_path`, `base64_data`, or `file_url` → get `file_url` (sync) Supported: Audio (MP3, WAV, FLAC, AAC, OGG, M4A, etc.). Max 100MB. Expire in 72h. Quota: 100 (default) / 500 (VIP). ### Step 3: Understand Intent - **Clear** ("make a chill lo-fi beat") → Go to Step 4 - **Ambiguous** ("I want some music") → Ask: "What kind of vibe or genre? Vocals or instrumental?" Ask only what's needed, when it's needed. ### Step 4: Gather Parameters Music has two required fields with no defaults — always collect both before calling `generate_music`. **Decision tree (ask in this order):** 1. **Vocals or instrumental?** → Sets `instrumental: true/false` 2. **Simple or custom mode?** - **Simple** (`custom_mode: false`): AI writes lyrics and picks style from your description - **Custom** (`custom_mode: true`): You control lyrics (`[Verse]`/`[Chorus]`/`[Bridge]`), style tags, title 3. **If custom mode**, additionally collect: - `style`: genre + mood + tempo tags (e.g., `"pop, upbeat, female vocals, 120bpm"`) - `title`: song name (max 80 chars) - `vocal_gender`: `m` or `f` — optional 4. **Optional for both modes:** - `duration`: target length 30–240s (omit to let model decide) - `negative_tags`: styles to exclude - `model`: default `suno-v4`. Suggest `suno-v5` for studio-grade quality. **Critical:** Both `custom_mode` and `instrumental` are required API fields with no defaults. Always set both before generating. ### Step 5: Generate & Poll 1. Call `generate_music` → tell user: *"Generating your music — ~Xs estimated."* 2. Poll `check_task` every **5–10s**. Report progress %. 3. After 3 consecutive `processing`: *"Still working..."* 4. **Completed:** Share URLs + metadata (title, duration, tags from `result_data[]`). *"Links expire in 24h — save promptly."* 5. **Failed:** Show error + suggestion. Offer retry if retryable. 6. **Timeout (5 min):** *"Taking longer than expected. Task ID: `{id}` — check again later."* ## Error Handling ### HTTP Errors | Error | Action | |-------|--------| | 401 | "API key isn't working. Check at evolink.ai/dashboard/keys" | | 402 | "Balance is low. Add credits at evolink.ai/dashboard/billing" | | 429 | "Rate limited — wait 30s and retry" | | 503 | "Servers busy — retry in a minute" | ### Task Errors (status: "failed") | Code | Retry? | Action | |------|--------|--------| | `content_policy_violation` | No | Revise prompt or lyrics | | `invalid_parameters` | No | Check values against model limits | | `generation_timeout` | Yes | Retry; simplify prompt if repeated | | `quota_exceeded` | Yes | Top up credits | | `resource_exhausted` | Yes | Wait 30–60s, retry | | `service_error` | Yes | Retry after 1 min | | `generation_failed_no_content` | Yes | Modify prompt, retry | Full error reference: `references/music-api-params.md` ## Without MCP Server Use Evolink's file hosting API for audio uploads (72h expiry). See `references/file-api.md` for curl commands. ## References - `references/music-api-params.md` — Complete API parameters, all 5 models, polling strategy, error codes - `references/file-api.md` — File hosting API (curl upload/list/delete)

path: references/file-api.md
content: # Evolink File Hosting API — Audio Upload for Music Workflows

When MCP tools are not available, use Evolink's file hosting service to upload audio files and get publicly accessible URLs for music continuation or remix workflows.

**Base URL:** `https://files-api.evolink.ai`
**Auth:** `Authorization: Bearer $EVOLINK_API_KEY`

## Upload a Local File

```bash
curl -X POST https://files-api.evolink.ai/api/v1/files/upload/stream \
  -H "Authorization: Bearer $EVOLINK_API_KEY" \
  -F "file=@/path/to/audio.mp3"
```

## Upload from URL

```bash
curl -X POST https://files-api.evolink.ai/api/v1/files/upload/url \
  -H "Authorization: Bearer $EVOLINK_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"file_url": "https://example.com/audio.mp3"}'
```

## Response

```json
{
  "data": {
    "file_id": "file_abc123",
    "file_url": "https://...",
    "download_url": "https://...",
    "file_size": 245120,
    "mime_type": "audio/mpeg",
    "expires_at": "2025-03-01T10:30:00Z"
  }
}
```

Use `file_url` from the response as a publicly accessible link. Files expire after **72 hours**.

## List Files & Check Quota

```bash
curl https://files-api.evolink.ai/api/v1/files/list?page=1&pageSize=20 \
  -H "Authorization: Bearer $EVOLINK_API_KEY"

curl https://files-api.evolink.ai/api/v1/files/quota \
  -H "Authorization: Bearer $EVOLINK_API_KEY"
```

## Delete a File

```bash
curl -X DELETE https://files-api.evolink.ai/api/v1/files/{file_id} \
  -H "Authorization: Bearer $EVOLINK_API_KEY"
```

**Supported:** Audio (MP3, WAV, FLAC, AAC, OGG, M4A, etc.). Max **100MB**. Quota: 100 files (default) / 500 (VIP).


path: references/music-api-params.md
content: # Evolink Music API — Parameter Reference

Complete API parameter reference for music generation tools.

**Base URL:** `https://api.evolink.ai`
**Auth:** `Authorization: Bearer {EVOLINK_API_KEY}`
**All generation endpoints are async** — they return `task_id` immediately; poll with `check_task`.

---

## generate_music

**Endpoint:** `POST /v1/audios/generations`

### Parameters

| Parameter | Type | Required | Default | Description |
|-----------|------|----------|---------|-------------|
| `prompt` | string | **Yes** | — | **Simple mode:** music description (max 500 chars). **Custom mode:** full lyrics with section tags like `[Verse]`, `[Chorus]`, `[Bridge]`, `[Outro]` (max 3000 chars for v4, 5000 for v4.5+). |
| `model` | enum | No | `suno-v4` | See Music Models below. |
| `custom_mode` | boolean | **Yes** | — | `false` = AI generates lyrics and style from your description. `true` = you control style, title, and lyrics. **No default — always set explicitly.** |
| `instrumental` | boolean | **Yes** | — | `true` = no vocals (instrumental only). `false` = with vocals. **No default — always set explicitly.** |
| `style` | string | No* | — | Comma-separated genre/mood/tempo tags. e.g. `"pop, upbeat, female vocals, 120bpm"`. *Required when `custom_mode: true`. |
| `title` | string | No* | — | Song title. Max 80 characters. *Required when `custom_mode: true`. |
| `negative_tags` | string | No | — | Styles to exclude. e.g. `"heavy metal, distorted guitar"`. |
| `vocal_gender` | enum | No | — | `m` (male) or `f` (female). Only effective in custom mode. |
| `duration` | integer | No | model decides | Target length in seconds (30–240s). |

### Two Modes

**Simple mode** (`custom_mode: false`):
- Provide a text description in `prompt`
- AI automatically generates lyrics, picks style and arrangement
- Easiest to use — just describe what you want

**Custom mode** (`custom_mode: true`):
- Write full lyrics in `prompt` with section markers: `[Verse]`, `[Chorus]`, `[Bridge]`, `[Outro]`
- Set `style` (genre/mood/tempo tags) and `title` (required in custom mode)
- Optionally set `vocal_gender` for male/female vocals

### Music Models (5, all BETA)

| Model | Quality | Max duration | Notes |
|-------|---------|--------------|-------|
| `suno-v4` *(default)* | Good | 120s | Balanced quality, economical |
| `suno-v4.5` | Better | 240s | Improved style control |
| `suno-v4.5plus` | Better | 240s | Extended v4.5 features |
| `suno-v4.5all` | Better | 240s | Full v4.5 feature set |
| `suno-v5` | Best | 240s | Studio-grade, best quality |

---

## check_task

**Endpoint:** `GET /v1/tasks/{task_id}`

### Response Fields

| Field | Type | Description |
|-------|------|-------------|
| `id` | string | Task ID |
| `model` | string | Model used for generation |
| `status` | enum | `pending` / `processing` / `completed` / `failed` |
| `progress` | integer | Progress percentage (0–100) |
| `results[]` | string[] | Direct result URLs — audio file download links |
| `result_data[].audio_url` | string | Audio download URL |
| `result_data[].stream_audio_url` | string | Streaming audio URL |
| `result_data[].title` | string | Music track title |
| `result_data[].duration` | number | Duration in seconds |
| `result_data[].tags` | string | Auto-generated style tags |
| `task_info.estimated_time` | integer | Estimated seconds remaining |
| `task_info.can_cancel` | boolean | Whether the task can be cancelled |
| `usage.credits_reserved` | number | Credits charged for this task |
| `error.code` | string | Error code (only when `status: "failed"`) |
| `error.message` | string | Error description (only when `status: "failed"`) |

All result URLs expire in **24 hours**.

### Status Values

| Status | Meaning | Action |
|--------|---------|--------|
| `pending` | Queued, not started | Continue polling |
| `processing` | Generation in progress | Continue polling, report `progress` |
| `completed` | Generation finished | Extract URLs from `results[]` or `result_data[]` |
| `failed` | Generation failed | Read `error.code` + `error.message`, surface to user |

---

## File Management API

**Base URL:** `https://files-api.evolink.ai`
**Auth:** `Authorization: Bearer {EVOLINK_API_KEY}` (same API key)

All file endpoints are **synchronous**.

### upload_file

| Method | Endpoint | Use when |
|--------|----------|----------|
| Base64 | `POST /api/v1/files/upload/base64` | Have base64 data |
| Stream | `POST /api/v1/files/upload/stream` | Have a local file |
| URL | `POST /api/v1/files/upload/url` | Have a remote URL |

**MCP Tool Parameters:**

| Parameter | Type | Required | Description |
|-----------|------|----------|-------------|
| `file_path` | string | One of three | Local file path |
| `base64_data` | string | One of three | Base64-encoded data |
| `file_url` | string | One of three | Remote URL |

### File Constraints

- **Supported:** Audio — MP3, WAV, FLAC, AAC, OGG, M4A, etc.
- **Max size:** 100MB
- **Expiry:** 72 hours
- **Quota:** 100 files (default) / 500 (VIP)

---

## Polling Strategy

| Type | Initial wait | Poll interval | Max wait |
|------|-------------|---------------|----------|
| Music | 5s | 5–10s | 5 minutes |

1. Submit `generate_music` → receive `task_id`
2. Wait 5 seconds
3. Call `check_task` → inspect `status`
4. If `pending`/`processing`: wait 5–10s, repeat
5. If `completed`: extract URLs from `results[]` + metadata from `result_data[]`
6. If `failed`: read `error.code`, surface to user

---

## Error Codes

### HTTP Status Codes

| Code | Meaning | Resolution |
|------|---------|------------|
| 400 | Bad request | Check required fields; revise prompt |
| 401 | Invalid API key | Verify at evolink.ai/dashboard/keys |
| 402 | Insufficient credits | Top up at evolink.ai/dashboard/billing |
| 429 | Rate limit exceeded | Wait 30–60s, retry |
| 500 | Server error | Retry after 1 minute |
| 503 | Service unavailable | Retry after 1–2 minutes |

### Task Error Codes

| Code | Retryable | Resolution |
|------|-----------|------------|
| `content_policy_violation` | No | Rephrase prompt or lyrics; avoid explicit content |
| `invalid_parameters` | No | Check param values — ensure `custom_mode` and `instrumental` are set |
| `model_unavailable` | No | Use `list_models` to find alternatives |
| `generation_timeout` | Yes | Retry; simplify prompt if repeated |
| `quota_exceeded` | Yes | Top up at evolink.ai/dashboard/billing |
| `resource_exhausted` | Yes | Wait 30–60s, retry |
| `service_error` | Yes | Retry after 1 minute |
| `generation_failed_no_content` | Yes | Modify prompt, retry |
| `upstream_error` | Yes | Retry after 1 minute |
| `unknown_error` | Yes | Retry; contact support if persistent |


Security scan verdicts — ClawScan: clean | static analysis: clean | VirusTotal: clean | SkillSpector: clean (LOW)