> ## Documentation Index
> Fetch the complete documentation index at: https://docs.nodylink.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Seedance 素材（火山标准 REST）

> 用与火山引擎一致的 /api/v3/asset/* 接口管理 Seedance 素材组和素材，处理完成后在视频生成中通过 asset:// 引用。

请注意：如果Seedance生成请求中未创建素材，后台将为其自动创建素材再提交任务。因此若无需素材管理则生成请求中直接传公网URL即可。

* 接口路径与火山引擎素材接口 `/api/v3/asset/*` 一致，只需把服务地址换成 `https://api.nodylink.com`，并用本平台的 API Key 鉴权。
* 所有操作都是 `POST`，请求体为 JSON，字段使用 snake\_case。
* 成功响应为 `{"result": {...}}`，错误使用 OpenAI 风格的错误体。
* 创建素材必须传 `group_id`，请先 [创建素材组](#创建素材组)。
* 素材按账户隔离：同一账户下的所有 API Key 共享素材组和素材，其他账户无法访问。
* 创建素材是异步的：接口立即返回素材 `Id`，请每 2 秒 [查询素材](#查询素材) 一次，直到 `Status` 为 `Active`，然后在视频生成中 [通过 asset:// 引用](#在视频生成中使用)。

> [!TIP]
>
> 三种接口格式功能相同、数据互通，按你的客户端选一种即可。也可以使用 [v1 接口](https://docs.nodylink.com/api-reference/videos/seedance-asset/v1.md) 或 [火山 SDK Action](https://docs.nodylink.com/api-reference/videos/seedance-asset/volc-action.md)。

```bash cURL theme={null}
curl https://api.nodylink.com/api/v3/asset/create \
  -H "Authorization: Bearer sk-你的密钥" \
  -H "Content-Type: application/json" \
  -d '{
    "group_id": "group-20261031114658-tsb52",
    "url": "https://example.com/character.png",
    "asset_type": "Image",
    "name": "character.png"
  }'
```

```python Python theme={null}
import time
import requests

API_KEY = "sk-你的密钥"
BASE = "https://api.nodylink.com/api/v3/asset"
headers = {"Authorization": f"Bearer {API_KEY}"}


def call(path: str, body: dict) -> dict:
    resp = requests.post(f"{BASE}{path}", headers=headers, json=body)
    data = resp.json()
    if not resp.ok:
        raise RuntimeError(data["error"]["message"])
    return data["result"]


group_id = call("/groups", {"name": "角色素材"})["Id"]
asset_id = call("/create", {
    "group_id": group_id,
    "url": "https://example.com/character.png",
    "asset_type": "Image",
    "name": "character.png",
})["Id"]

while True:
    status = call("/get", {"id": asset_id})["Status"]
    if status == "Active":
        break
    if status == "Failed":
        raise RuntimeError("素材处理失败，请检查 URL、格式、尺寸或时长")
    time.sleep(2)

print(f"asset://{asset_id}")
```

```javascript Node.js theme={null}
const API_KEY = "sk-你的密钥";
const BASE = "https://api.nodylink.com/api/v3/asset";

const call = async (path, body) => {
  const resp = await fetch(`${BASE}${path}`, {
    method: "POST",
    headers: {
      Authorization: `Bearer ${API_KEY}`,
      "Content-Type": "application/json",
    },
    body: JSON.stringify(body),
  });
  const data = await resp.json();
  if (!resp.ok) throw new Error(data.error?.message ?? `HTTP ${resp.status}`);
  return data.result;
};

const { Id: groupId } = await call("/groups", { name: "角色素材" });
const { Id: assetId } = await call("/create", {
  group_id: groupId,
  url: "https://example.com/character.png",
  asset_type: "Image",
  name: "character.png",
});

while (true) {
  const { Status } = await call("/get", { id: assetId });
  if (Status === "Active") break;
  if (Status === "Failed") throw new Error("素材处理失败，请检查 URL、格式、尺寸或时长");
  await new Promise((r) => setTimeout(r, 2000));
}

console.log(`asset://${assetId}`);
```

```json 200 theme={null}
{
  "result": {
    "Id": "asset-20261031114703-96kw4"
  }
}
```

```json 400 theme={null}
{
  "error": {
    "message": "group_id is required (request id: 2026103112000012345678)",
    "type": "new_api_error",
    "param": "",
    "code": "missing_group_id"
  }
}
```

```json 403 theme={null}
{
  "error": {
    "message": "素材或素材组不存在，或当前账号无权访问 (request id: 2026103112000012345678)",
    "type": "new_api_error",
    "param": "",
    "code": "seedance_asset_forbidden"
  }
}
```

## 鉴权

**Authorization** `string` *required*

`Bearer <API Key>`。在 [API 密钥](https://nodylink.com/dashboard/keys) 页面创建。

## 接口一览

| 操作 | 路径 |
| - | - |
| [创建素材组](#创建素材组) | `POST /api/v3/asset/groups` |
| [列出素材组](#列出素材组) | `POST /api/v3/asset/groups/list` |
| [查询素材组](#查询素材组) | `POST /api/v3/asset/groups/get` |
| [更新素材组](#更新素材组) | `POST /api/v3/asset/groups/update` |
| [删除素材组](#删除素材组) | `POST /api/v3/asset/groups/delete` |
| [创建素材](#创建素材) | `POST /api/v3/asset/create` |
| [查询素材](#查询素材) | `POST /api/v3/asset/get` |
| [列出素材](#列出素材) | `POST /api/v3/asset/list` |
| [更新素材](#更新素材) | `POST /api/v3/asset/update` |
| [删除素材](#删除素材) | `POST /api/v3/asset/delete` |

## 素材组

素材组用于归类素材。素材组和组内素材只对创建它的账户可见。

### 创建素材组

`POST /api/v3/asset/groups`

| 字段 | 类型 | 说明 |
| - | - | - |
| `name` | string | 必填，素材组名称，不超过 64 个字符 |
| `description` | string | 选填，素材组描述，不超过 1024 个字符 |

```json 200 theme={null}
{
  "result": {
    "Id": "group-20261031114658-tsb52"
  }
}
```

请保存 `result.Id`，后续操作通过它指定素材组。

### 列出素材组

`POST /api/v3/asset/groups/list`

列出当前账户创建的素材组，最新创建的排在前面。请求体可以为空。

| 字段 | 类型 | 说明 |
| - | - | - |
| `page_number` | integer | 选填，页码，从 1 开始，默认 `1` |
| `page_size` | integer | 选填，每页条数，取值 1～100，默认 `10` |

```json 200 theme={null}
{
  "result": {
    "Items": [
      {
        "Id": "group-20261031114658-tsb52",
        "Name": "角色素材",
        "Description": "主角参考图",
        "CreateTime": "2026-10-31T03:46:58Z"
      }
    ],
    "PageNumber": 1,
    "PageSize": 10,
    "TotalCount": 1
  }
}
```

### 查询素材组

`POST /api/v3/asset/groups/get`

| 字段 | 类型 | 说明 |
| - | - | - |
| `id` | string | 必填，素材组 ID。也可以写成 `group_id` |

```json 200 theme={null}
{
  "result": {
    "Id": "group-20261031114658-tsb52",
    "Name": "角色素材",
    "Description": "主角参考图",
    "GroupType": "AIGC",
    "ProjectName": "default",
    "CreateTime": "2026-10-31T03:46:58Z",
    "UpdateTime": "2026-10-31T03:46:58Z"
  }
}
```

### 更新素材组

`POST /api/v3/asset/groups/update`

`name` 和 `description` 至少传一个，只更新传入的字段。

| 字段 | 类型 | 说明 |
| - | - | - |
| `id` | string | 必填，素材组 ID。也可以写成 `group_id` |
| `name` | string | 选填，新名称，不能为空字符串，不超过 64 个字符 |
| `description` | string | 选填，新描述，不超过 1024 个字符 |

```json 200 theme={null}
{
  "result": {
    "Id": "group-20261031114658-tsb52"
  }
}
```

### 删除素材组

`POST /api/v3/asset/groups/delete`

> [!WARNING]
>
> 删除素材组会同时删除组内的所有素材，且无法恢复。已提交的视频任务不受影响，但之后无法再引用这些素材。

| 字段 | 类型 | 说明 |
| - | - | - |
| `id` | string | 必填，素材组 ID。也可以写成 `group_id` |

```json 200 theme={null}
{
  "result": {
    "Id": "group-20261031114658-tsb52"
  }
}
```

## 素材

### 创建素材

`POST /api/v3/asset/create`

把公网素材登记到指定素材组，立即返回素材 `Id`，不等待处理完成。

| 字段 | 类型 | 说明 |
| - | - | - |
| `group_id` | string | 必填，素材组 ID，必须是当前账户创建的素材组 |
| `url` | string | 必填，素材的公网直链，必须以 `http://` 或 `https://` 开头 |
| `asset_type` | string | 选填，素材类型：`Image`、`Video` 或 `Audio`，不区分大小写，默认 `Image` |
| `name` | string | 选填，素材名称，不超过 64 个字符。不传时使用 URL 中的文件名 |

```json 200 theme={null}
{
  "result": {
    "Id": "asset-20261031114703-96kw4"
  }
}
```

### 支持格式与限制

| 素材类型 | 格式 | 限制 |
| - | - | - |
| `Image` | jpeg、png、webp、bmp、tiff、gif、heic / heif | 宽高比 0.4～2.5，宽高 300～6000 px，单张小于 30 MB |
| `Video` | mp4、mov | 时长 1.8～15.2 秒，高度 300～6000 px |
| `Audio` | mp3、wav | 需提供可直接下载的音频文件 URL |

素材 URL 必须是公网直链，无需登录即可直接下载，建议使用 HTTPS。不支持本地文件上传，也不支持 `data:` 格式的 Base64 数据。

### 查询素材

`POST /api/v3/asset/get`

创建后素材可能仍在处理。建议每 2 秒查询一次，直到 `Status` 为 `Active`。

| 字段 | 类型 | 说明 |
| - | - | - |
| `id` | string | 必填，素材 ID |

```json 200 theme={null}
{
  "result": {
    "Id": "asset-20261031114703-96kw4",
    "Name": "character.png",
    "AssetType": "Image",
    "GroupId": "group-20261031114658-tsb52",
    "Status": "Active",
    "URL": "https://ark-media-asset.tos-cn-beijing.volces.com/...png?X-Tos-Signature=...",
    "Moderation": {
      "Strategy": "Default"
    },
    "ProjectName": "default",
    "CreateTime": "2026-10-31T03:47:03Z",
    "UpdateTime": "2026-10-31T03:47:04Z"
  }
}
```

| 字段 | 类型 | 说明 |
| - | - | - |
| `result.Id` | string | 素材 ID |
| `result.Name` | string | 素材名称 |
| `result.AssetType` | string | 素材类型：`Image`、`Video` 或 `Audio` |
| `result.GroupId` | string | 所属素材组 ID |
| `result.Status` | string | 处理状态，见 [处理状态](#处理状态) |
| `result.URL` | string | 处理后的素材访问地址，是有有效期的签名 URL，不能作为素材的永久标识 |
| `result.CreateTime` | string | 创建时间，UTC ISO 8601 格式 |
| `result.UpdateTime` | string | 最近更新时间，UTC ISO 8601 格式 |

### 处理状态

| 状态 | 含义 | 处理建议 |
| - | - | - |
| `Pending` / `Processing` | 处理中 | 继续轮询，建议间隔 2 秒 |
| `Active` | 处理完成，素材可用 | 停止轮询，在视频生成中引用 |
| `Failed` | 处理失败 | 停止轮询，检查素材 URL 能否直接下载，以及格式、尺寸、时长是否符合 [限制](#支持格式与限制) |

### 列出素材

`POST /api/v3/asset/list`

列出指定素材组内的素材。

| 字段 | 类型 | 说明 |
| - | - | - |
| `group_id` | string | 必填，素材组 ID |
| `page_number` | integer | 选填，页码，从 1 开始，默认 `1` |
| `page_size` | integer | 选填，每页条数，取值 1～100，默认 `10` |

```json 200 theme={null}
{
  "result": {
    "Items": [
      {
        "Id": "asset-20261031114703-96kw4",
        "Name": "character.png",
        "AssetType": "Image",
        "GroupId": "group-20261031114658-tsb52",
        "Status": "Active",
        "URL": "https://ark-media-asset.tos-cn-beijing.volces.com/...png?X-Tos-Signature=...",
        "Moderation": {
          "Strategy": "Default"
        },
        "ProjectName": "default",
        "CreateTime": "2026-10-31T03:47:03Z",
        "UpdateTime": "2026-10-31T03:47:04Z"
      }
    ],
    "PageNumber": 1,
    "PageSize": 10,
    "TotalCount": 1
  }
}
```

### 更新素材

`POST /api/v3/asset/update`

目前只支持修改素材名称。

| 字段 | 类型 | 说明 |
| - | - | - |
| `id` | string | 必填，素材 ID |
| `name` | string | 必填，新名称，不能为空，不超过 64 个字符 |

```json 200 theme={null}
{
  "result": {
    "Id": "asset-20261031114703-96kw4"
  }
}
```

### 删除素材

`POST /api/v3/asset/delete`

| 字段 | 类型 | 说明 |
| - | - | - |
| `id` | string | 必填，素材 ID |

```json 200 theme={null}
{
  "result": {}
}
```

删除成功时 `result` 可能为空对象，也可能带 `Id`，请以 HTTP 200 判断成功。删除后再访问该素材会返回 403 `seedance_asset_forbidden`。

## 在视频生成中使用

素材变为 `Active` 后，在 [Seedance 视频生成](https://docs.nodylink.com/api-reference/videos/seedance/seedance-2-0.md) 请求的 `content` 中，把对应的 URL 写成 `asset://<Id>`：

```json theme={null}
{
  "model": "Doubao-Seedance-2.0",
  "content": [
    {"type": "text", "text": "图片1中的角色在海边奔跑，镜头跟随"},
    {"type": "image_url", "image_url": {"url": "asset://asset-20261031114703-96kw4"}, "role": "reference_image"}
  ],
  "ratio": "16:9",
  "duration": 5
}
```

视频和音频素材同理，分别写在 `video_url.url` 和 `audio_url.url` 中。

> [!WARNING]
>
> * 素材 ID 只能在本平台的 Seedance 视频生成中使用。
> * 素材详情里的 `URL` 是会过期的签名地址，请保存素材 `Id`，不要保存 `URL`。

## 错误响应

错误使用 OpenAI 风格的错误体，格式见 [错误码](https://docs.nodylink.com/errors.md)。`message` 末尾的 `(request id: ...)` 是本次请求的唯一 ID，反馈问题时请附上。

| 错误码 | 状态码 | 说明 |
| - | - | - |
| `invalid_request` | 400 | 请求体不是合法的 JSON |
| `invalid_url` | 400 | `url` 缺失、不是 http(s) 链接，或使用了 `data:` 格式 |
| `invalid_asset_type` | 400 | `asset_type` 不是 `Image`、`Video`、`Audio` 之一 |
| `invalid_asset_name` | 400 | 素材名称超过 64 个字符 |
| `missing_asset_id` | 400 | 未传素材 ID |
| `missing_asset_name` | 400 | 更新素材时未传 `name`，或为空 |
| `missing_group_id` | 400 | 未传素材组 ID，创建素材时也必须传 |
| `missing_group_name` | 400 | 创建素材组时未传 `name`，或更新时 `name` 为空字符串 |
| `invalid_group_name` | 400 | 素材组名称超过 64 个字符 |
| `invalid_group_description` | 400 | 素材组描述超过 1024 个字符 |
| `missing_update_fields` | 400 | 更新素材组时 `name` 和 `description` 都没传 |
| `invalid_page_number` | 400 | `page_number` 小于 1 |
| `invalid_page_size` | 400 | `page_size` 不在 1～100 之间 |
| — | 401 | API Key 缺失或无效 |
| `seedance_asset_forbidden` | 403 | 素材或素材组不存在、已删除或属于其他账户 |
| `seedance_upstream_bad_request` | 400 | 素材服务认为参数不合法，原因见 `message`，修正后再试 |
| `seedance_upstream_rejected` | 422 | 素材服务拒绝了请求，原因见 `message` |
| `seedance_upstream_rate_limited` | 429 | 素材服务限流，请退避后重试 |
| `seedance_upstream_denied` | 502 | 素材服务拒绝访问，资源可能已被删除 |
| `seedance_upstream_failed` | 502 | 素材服务异常或超时，请稍后重试 |
| `seedance_upstream_bad_response` | 502 | 素材服务返回的数据缺少素材 ID，请稍后重试 |
| `seedance_asset_store_failed` | 500 | 保存素材归属失败，请稍后重试 |

> [!NOTE]
>
> 素材管理接口上线前通过旧版接口创建的素材没有账户归属记录，查询、更新、删除时会返回 403，但仍可在视频生成中通过 `asset://<Id>` 引用。


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.