Skip to content

API reference

Account and API keys API

Check API health, read the account behind an API key, and create, list, or revoke scoped API keys.

BetaUpdated

Base URL
https://lyricwinter.com/api/v1
Authentication
Authorization: Bearer lw_…
Contract
openapi.json

Check API health

GET/health

No authentication

Returns a static payload when the LyricWinter API is reachable. It needs no authentication and performs no account checks.

Response 200

Stable API health response. Fields below are inside data.

  • oktruerequired
  • service"lyricwinter"required
  • version"v1"required
curl "https://lyricwinter.com/api/v1/health" \
  -H "Authorization: Bearer $LYRICWINTER_API_KEY"
Response 200 (example)
{
  "data": {
    "ok": true,
    "service": "lyricwinter",
    "version": "v1"
  },
  "request_id": "req_01J9Z3K8QF4"
}

Get the current account

GET/me

Scope account:read

Returns the profile of the account that owns the API key: its ID, username, display name, avatar URL, and email.

Response 200

Current account profile. Fields below are inside data.

  • profileobjectrequired
    5 child attributes
    • idstringrequired
    • usernamestring | nullrequired3–30 chars
    • namestring | nullrequiredmax 100 chars
    • imagestring | nullrequireduri
    • emailstring | nullrequiredemail

Errors 401, 403, 500 use the standard error envelope.

curl "https://lyricwinter.com/api/v1/me" \
  -H "Authorization: Bearer $LYRICWINTER_API_KEY"
Response 200 (example)
{
  "data": {
    "profile": {
      "id": "8f14e45f-ceea-4e7a-9c2d-3b1a5f2e7c10",
      "username": "string",
      "name": "My integration",
      "image": "https://lyricwinter.com/…",
      "email": "[email protected]"
    }
  },
  "request_id": "req_01J9Z3K8QF4"
}

List API keys

GET/api-keys

Scope api_keys:read

Lists metadata for the account's API keys, including name, scopes, expiry, last use, and revocation time. Raw keys are never returned.

Response 200

Caller-owned API key metadata without raw key material or token hashes. Fields below are inside data.

  • api_keysarray of objectrequired
    9 item attributes
    • idstringrequireduuid
    • namestringrequired1–80 chars
    • token_prefixstringrequiredpattern ^lw_[A-Za-z0-9_-]{8,32}$

      Safe display prefix for identifying a key.

    • scopesarray of stringrequired

      One ofaccount:readaccount:writeapi_keys:readapi_keys:writeaudio_runs:readaudio_runs:writebilling:readbilling:writedemo_videos:readdemo_videos:writefeedback:writeprojects:readprojects:writereactions:readreactions:writestories:readstories:writestudio:readstudio:writevoice_pins:readvoice_pins:writevoice_actors:readvoice_shares:readvoice_shares:writevoices:readvoices:write

    • expires_atstring | nullrequireddate-time
    • last_used_atstring | nullrequireddate-time
    • revoked_atstring | nullrequireddate-time
    • created_atstringrequireddate-time
    • updated_atstringrequireddate-time

Errors 401, 403, 500 use the standard error envelope.

curl "https://lyricwinter.com/api/v1/api-keys" \
  -H "Authorization: Bearer $LYRICWINTER_API_KEY"
Response 200 (example)
{
  "data": {
    "api_keys": [
      {
        "id": "8f14e45f-ceea-4e7a-9c2d-3b1a5f2e7c10",
        "name": "My integration",
        "token_prefix": "string",
        "scopes": [
          "account:read"
        ],
        "expires_at": "2026-09-30T17:00:00.000Z",
        "last_used_at": "2026-09-30T17:00:00.000Z",
        "revoked_at": "2026-09-30T17:00:00.000Z",
        "created_at": "2026-09-30T17:00:00.000Z",
        "updated_at": "2026-09-30T17:00:00.000Z"
      }
    ]
  },
  "request_id": "req_01J9Z3K8QF4"
}

Create an API key

POST/api-keys

Scope api_keys:write

Creates a scoped API key. The response contains raw_key exactly once; LyricWinter stores only a hash. When you call this endpoint with an API key, the new key can only have scopes that the calling key already holds.

Request body application/json

  • namestringrequired1–80 chars
  • scopesarray of stringrequiredmin 1 items

    Duplicate scopes are accepted and deduplicated.

    One ofaccount:readaccount:writeapi_keys:readapi_keys:writeaudio_runs:readaudio_runs:writebilling:readbilling:writedemo_videos:readdemo_videos:writefeedback:writeprojects:readprojects:writereactions:readreactions:writestories:readstories:writestudio:readstudio:writevoice_pins:readvoice_pins:writevoice_actors:readvoice_shares:readvoice_shares:writevoices:readvoices:write

  • expires_atstring | nulldate-time

    Optional expiration timestamp. Null or omitted creates a non-expiring key.

Response 201

API key created. The raw key is returned only in this response. Fields below are inside data.

  • api_keyobjectrequired
    9 child attributes
    • idstringrequireduuid
    • namestringrequired1–80 chars
    • token_prefixstringrequiredpattern ^lw_[A-Za-z0-9_-]{8,32}$

      Safe display prefix for identifying a key.

    • scopesarray of stringrequired

      One ofaccount:readaccount:writeapi_keys:readapi_keys:writeaudio_runs:readaudio_runs:writebilling:readbilling:writedemo_videos:readdemo_videos:writefeedback:writeprojects:readprojects:writereactions:readreactions:writestories:readstories:writestudio:readstudio:writevoice_pins:readvoice_pins:writevoice_actors:readvoice_shares:readvoice_shares:writevoices:readvoices:write

    • expires_atstring | nullrequireddate-time
    • last_used_atstring | nullrequireddate-time
    • revoked_atstring | nullrequireddate-time
    • created_atstringrequireddate-time
    • updated_atstringrequireddate-time
  • raw_keystringrequiredpattern ^lw_[A-Za-z0-9_-]{8,32}_[A-Za-z0-9_-]+$

    Display-once raw API key. The server stores only a SHA-256 hash.

Errors 400, 401, 403, 409, 500 use the standard error envelope.

curl -X POST "https://lyricwinter.com/api/v1/api-keys" \
  -H "Authorization: Bearer $LYRICWINTER_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
  "name": "My integration",
  "scopes": [
    "account:read"
  ]
}'
Response 201 (example)
{
  "data": {
    "api_key": {
      "id": "8f14e45f-ceea-4e7a-9c2d-3b1a5f2e7c10",
      "name": "My integration",
      "token_prefix": "string",
      "scopes": [
        "account:read"
      ],
      "expires_at": "2026-09-30T17:00:00.000Z",
      "last_used_at": "2026-09-30T17:00:00.000Z",
      "revoked_at": "2026-09-30T17:00:00.000Z",
      "created_at": "2026-09-30T17:00:00.000Z",
      "updated_at": "2026-09-30T17:00:00.000Z"
    },
    "raw_key": "string"
  },
  "request_id": "req_01J9Z3K8QF4"
}

Revoke an API key

DELETE/api-keys/{apiKeyId}

Scope api_keys:write

Revokes one of the account's API keys immediately. Revoking a key that is already revoked succeeds without changes.

Path parameters

  • apiKeyIdstringrequireduuid

Response 200

Caller-owned API key was revoked, or was already revoked. Fields below are inside data.

  • oktruerequired
  • api_keyobjectrequired
    9 child attributes
    • idstringrequireduuid
    • namestringrequired1–80 chars
    • token_prefixstringrequiredpattern ^lw_[A-Za-z0-9_-]{8,32}$

      Safe display prefix for identifying a key.

    • scopesarray of stringrequired

      One ofaccount:readaccount:writeapi_keys:readapi_keys:writeaudio_runs:readaudio_runs:writebilling:readbilling:writedemo_videos:readdemo_videos:writefeedback:writeprojects:readprojects:writereactions:readreactions:writestories:readstories:writestudio:readstudio:writevoice_pins:readvoice_pins:writevoice_actors:readvoice_shares:readvoice_shares:writevoices:readvoices:write

    • expires_atstring | nullrequireddate-time
    • last_used_atstring | nullrequireddate-time
    • revoked_atstring | nullrequireddate-time
    • created_atstringrequireddate-time
    • updated_atstringrequireddate-time

Errors 400, 401, 403, 404, 500 use the standard error envelope.

curl -X DELETE "https://lyricwinter.com/api/v1/api-keys/$API_KEY_ID" \
  -H "Authorization: Bearer $LYRICWINTER_API_KEY"
Response 200 (example)
{
  "data": {
    "ok": true,
    "api_key": {
      "id": "8f14e45f-ceea-4e7a-9c2d-3b1a5f2e7c10",
      "name": "My integration",
      "token_prefix": "string",
      "scopes": [
        "account:read"
      ],
      "expires_at": "2026-09-30T17:00:00.000Z",
      "last_used_at": "2026-09-30T17:00:00.000Z",
      "revoked_at": "2026-09-30T17:00:00.000Z",
      "created_at": "2026-09-30T17:00:00.000Z",
      "updated_at": "2026-09-30T17:00:00.000Z"
    }
  },
  "request_id": "req_01J9Z3K8QF4"
}