# AI Creative MCP 使用方接入文档
## 1. 接口概览
AI Creative 通过 MCP Streamable HTTP 对外提供素材上传、模型查询、生成任务提交和任务状态查询能力。
| 项目 | 说明 |
| --- | --- |
| MCP 地址 | `beta环境POST https://aicreative-api-beta.creatiads.com/api/mcp`
`prod环境POST https://aicreative-api.creatiads.com/api/mcp` |
| 协议版本 | MCP `2026-09-23` |
| 传输方式 | Stateless Streamable HTTP |
| 身份凭证 | 调用方所属三方系统签发的 Token |
| 会话要求 | 无会话,不使用 `mcp-session-id` |
| 最大请求体 | 2 MiB;媒体文件本身通过公网 URL 提供,不支持在 MCP 请求中传 base64 |
当前提供 5 个工具:
| 工具 | 用途 | 是否产生业务数据 |
| --- | --- | --- |
| `upload_media` | 通过公网 URL 上传图片或视频 | 是,创建素材记录 |
| `list_models` | 查询当前用户可使用的模型 | 否 |
| `get_model_parameters` | 查询指定模型的参数定义 | 否 |
| `submit_generation_task` | 提交图片或视频生成任务 | 是,会按正式业务规则计费、扣分和调度 |
| `get_generation_task` | 查询任务状态和生成结果 | 否 |
## 2. 鉴权方式
### 2.1 必须携带的 Header
每一次 MCP HTTP 请求都必须携带以下 Header:
#beta
X-Embed-Parent-Origin: [https://app-beta.creatiads.com](https://app-beta.creatiads.com)
#prod
X-Embed-Parent-Origin: [https://app.creatiads.com](https://app.creatiads.com)
```http
Authorization: Bearer
X-Embed-Parent-Origin:
Content-Type: application/json
Accept: application/json, text/event-stream
```
可选 Header:
```http
language: zh
MCP-Protocol-Version: 2026-09-23
```
| Header | 必填 | 说明 |
| --- | --- | --- |
| `Authorization` | 是 | 必须为 `Bearer `;这里传三方系统 Token,不是 AI Creative 本地 JWT |
| `X-Embed-Parent-Origin` | 是 | 标识 Token 所属的三方系统,值必须与服务端预先配置的 Origin 完全一致 |
| `Content-Type` | 是 | 固定为 `application/json` |
| `Accept` | 是 | 建议同时声明 `application/json, text/event-stream`,兼容 JSON 和 SSE 响应 |
| `language` | 否 | 传 `zh` 返回中文业务提示;不传或不是 `zh` 时默认英文 |
| `MCP-Protocol-Version` | 否 | 使用原始 HTTP 接入时建议传协商后的协议版本 |
> `X-Embed-Parent-Origin` 只用于确认三方系统,不代替 Token 身份校验。
### 2.2 每次请求的认证过程
服务端对每一个 MCP HTTP 请求执行以下步骤:
1. 根据 `X-Embed-Parent-Origin` 找到对应的已启用三方系统。
2. 使用 `Authorization` 中的 Token 实时请求该三方系统,获取三方用户信息。
3. 将三方用户与 AI Creative 本地账号进行匹配。
4. 已存在账号时同步用户资料和授权;不存在时创建本地账号及三方身份绑定。
5. 认证完成后,以该本地用户身份执行本次 MCP 工具调用。
服务端不缓存 MCP 登录会话,也不生成 `mcp-session-id`。因此不能只在第一次请求传 Token,后续的 `tools/list`、`tools/call` 等每个请求都必须重复携带完整认证 Header。
## 3. MCP Client 配置示例
不同 MCP Client 的配置文件格式可能不同,下面为通用示例:
```json
{
"mcpServers": {
"aicreative": {
"type": "http",
"url": "https://aicreative-api-beta.creatiads.com/api/mcp",
"headers": {
"Authorization": "Bearer ",
"X-Embed-Parent-Origin": "https://app-beta.creatiads.com",
"language": "en"
}
}
}
}
```
标准 MCP Client 通常会自动完成 `initialize` 和工具发现。若使用 Apifox、curl 等工具手工联调,可以直接发送 `tools/list` 或 `tools/call`。
## 4. JSON-RPC 请求格式
### 4.1 查询工具列表
```json
{
"jsonrpc": "2.0",
"id": 1,
"method": "tools/list",
"params": {}
}
```
### 4.2 调用工具
```json
{
"jsonrpc": "2.0",
"id": 2,
"method": "tools/call",
"params": {
"name": "",
"arguments": {}
}
}
```
`id` 由调用方生成,用于匹配请求和响应。每次请求建议使用不同的 `id`。
### 4.3 成功响应
工具成功时,结果同时提供文本和结构化数据。调用方应优先读取 `structuredContent`;不支持结构化结果的旧客户端可以解析 `content[0].text` 中的 JSON 字符串。
```json
{
"jsonrpc": "2.0",
"id": 2,
"result": {
"content": [
{
"type": "text",
"text": "{\"models\":[]}"
}
],
"structuredContent": {
"models": [ ]
},
"isError": false
}
}
```
### 4.4 工具业务失败
参数校验、余额不足、素材无权限、模型不可用等工具业务错误使用 HTTP 200 返回,`result.isError` 为 `true`。错误详情是 `content[0].text` 中的 JSON 字符串:
```json
{
"jsonrpc": "2.0",
"id": 2,
"result": {
"content": [
{
"type": "text",
"text": "{\"code\":400,\"message\":\"Invalid request\",\"requestId\":\"01J...\"}"
}
],
"isError": true
}
}
```
业务失败时不会返回成功结构的 `structuredContent`。调用方不能只根据 HTTP 状态判断工具是否成功,还必须检查 `result.isError`。
## 5. 推荐调用流程
```text
list_models
↓
get_model_parameters
↓
upload_media(仅在需要图片、视频或首尾帧输入时调用)
↓
submit_generation_task
↓
get_generation_task(轮询至终态)
```
接入时应注意:
1. 模型 ID 不应写死。先调用 `list_models` 获取当前用户可用的 `modelConfigId`。
2. 模型可用参数、取值和限制以 `get_model_parameters` 的实时返回为准。
3. 素材输入优先传 `upload_media` 返回的 `assetId`。
4. 每个新的生成请求使用新的 `clientRequestId`;同一请求重试时复用原值。
5. 生成任务是异步任务,提交成功后使用返回的 `taskId` 查询状态。
## 6. 工具说明
### 6.1 `upload_media`
通过公网 HTTP(S) URL 导入一张图片或一个视频,返回后续生成任务可使用的稳定素材 ID 和当前访问 URL。
#### 输入参数
| 字段 | 类型 | 必填 | 说明 |
| --- | --- | --- | --- |
| `sourceUrl` | string | 是 | 可由服务端访问的公网 HTTP(S) 图片或视频 URL,最长 4096 字符 |
| `assetType` | string | 是 | `IMAGE` 或 `VIDEO` |
| `assetName` | string | 是 | 素材名称,1~200 字符 |
不支持本地文件路径、multipart 文件或 base64 内容。`assetType` 必须与 URL 实际指向的媒体类型一致。
#### 请求示例
```json
{
"jsonrpc": "2.0",
"id": 10,
"method": "tools/call",
"params": {
"name": "upload_media",
"arguments": {
"sourceUrl": "https://cdn.example.com/input/reference.jpg",
"assetType": "IMAGE",
"assetName": "reference-image.jpg"
}
}
}
```
#### `structuredContent` 示例
```json
{
"asset": {
"assetId": 506500001,
"url": "https://cdn.example.com/material/506500001.jpg",
"thumbnailUrl": "https://cdn.example.com/material/506500001-thumbnail.jpg",
"assetName": "reference-image.jpg",
"assetType": "IMAGE",
"fileSizeBytes": 245760,
"metadata": {
"width": 1024,
"height": 1024
}
}
}
```
#### 输出字段
| 字段 | 类型 | 说明 |
| --- | --- | --- |
| `asset.assetId` | integer | 稳定素材 ID;提交生成任务时主要使用此字段 |
| `asset.url` | string | 当前素材 URL |
| `asset.thumbnailUrl` | string/null | 缩略图 URL |
| `asset.assetName` | string | 素材名称 |
| `asset.assetType` | string | `IMAGE` 或 `VIDEO` |
| `asset.fileSizeBytes` | integer/null | 文件大小,单位字节 |
| `asset.metadata` | object/null | 媒体元信息,例如宽高、时长等;具体字段取决于素材类型 |
该工具会创建素材数据,重复调用不保证返回同一个 `assetId`。
### 6.2 `list_models`
查询当前认证用户可以使用的图片或视频模型。
#### 输入参数
| 字段 | 类型 | 必填 | 说明 |
| --- | --- | --- | --- |
| `modelType` | string | 是 | `IMAGE` 或 `VIDEO` |
#### 请求示例
```json
{
"jsonrpc": "2.0",
"id": 20,
"method": "tools/call",
"params": {
"name": "list_models",
"arguments": {
"modelType": "VIDEO"
}
}
}
```
#### `structuredContent` 示例
以下 ID 和模型信息仅用于展示响应结构,实际值以接口返回为准。
```json
{
"models": [
{
"modelConfigId": 1103,
"modelType": "VIDEO",
"locale": "en",
"displayName": "Example Video Model",
"description": "Example model description",
"iconUrl": "https://cdn.example.com/model/icon.png",
"tagCodes": ["TEXT_TO_VIDEO", "IMAGE_TO_VIDEO"],
"minPoints": 20,
"estimatedTimeSeconds": 120
}
]
}
```
#### 输出字段
| 字段 | 类型 | 说明 |
| --- | --- | --- |
| `models[].modelConfigId` | integer | 模型配置 ID,后续查询参数和提交任务时使用 |
| `models[].modelType` | string | 模型类型,`IMAGE` 或 `VIDEO` |
| `models[].locale` | string/null | 模型信息语言 |
| `models[].displayName` | string | 模型展示名称 |
| `models[].description` | string/null | 模型说明 |
| `models[].iconUrl` | string/null | 模型图标 URL |
| `models[].tagCodes` | string\[\]/null | 模型能力标签 |
| `models[].minPoints` | integer/null | 最低积分提示;最终消耗以提交时正式报价为准 |
| `models[].estimatedTimeSeconds` | integer/null | 预计生成时长,单位秒,仅作参考 |
### 6.3 `get_model_parameters`
查询指定模型当前的输入、输出和业务参数定义。提交生成任务前应调用本工具,不要自行猜测参数值。
#### 输入参数
| 字段 | 类型 | 必填 | 说明 |
| --- | --- | --- | --- |
| `modelConfigId` | integer | 是 | `list_models` 返回的模型配置 ID,必须大于 0 |
#### 请求示例
```json
{
"jsonrpc": "2.0",
"id": 30,
"method": "tools/call",
"params": {
"name": "get_model_parameters",
"arguments": {
"modelConfigId": 1103
}
}
}
```
#### `structuredContent` 响应结构
```json
{
"model": {
"modelConfigId": 1103,
"modelType": "VIDEO",
"locale": "en",
"displayName": "Example Video Model",
"description": "Example model description",
"iconUrl": "https://cdn.example.com/model/icon.png",
"tagCodes": ["TEXT_TO_VIDEO", "IMAGE_TO_VIDEO"],
"minPoints": 20,
"estimatedTimeSeconds": 120,
"inputSettings": {},
"outputSettings": {},
"businessSettings": null
}
}
```
`inputSettings`、`outputSettings` 和 `businessSettings` 是模型动态配置,不同模型的结构可能不同。调用方必须保留并解析实际返回内容,以它声明的必填项、选项和限制构造 `submit_generation_task` 参数。
### 6.4 `submit_generation_task`
提交原创图片或视频生成任务。
该工具进入正式业务链路,会执行素材归属校验、模型可用性校验、价格计算、积分扣除、任务持久化和生成调度。任务失败时沿用现有退款或补偿机制。联调阶段应使用测试环境和测试账号。
#### 输入参数
| 字段 | 类型 | 必填 | 说明 |
| --- | --- | --- | --- |
| `clientRequestId` | string | 是 | 调用方生成的幂等 ID,1~128 字符 |
| `generationType` | string | 是 | `IMAGE` 或 `VIDEO`,必须与所选模型类型一致 |
| `modelConfigId` | integer | 是 | `list_models` 返回的模型配置 ID |
| `prompt` | string | 是 | 提示词,1~10000 字符 |
| `negativePrompt` | string | 否 | 反向提示词,最长 10000 字符 |
| `imageAssets` | object\[\] | 否 | 参考图片列表 |
| `videoAssets` | object\[\] | 否 | 参考视频列表 |
| `frame` | object | 否 | 视频首帧和尾帧素材 |
| `parameters` | object | 否 | 模型生成参数 |
素材引用结构:
| 字段 | 类型 | 必填 | 说明 |
| --- | --- | --- | --- |
| `assetId` | integer | 是 | `upload_media` 返回的素材 ID |
| `url` | string | 否 | 兼容字段,最长 4096 字符;服务端会根据 `assetId` 获取最新 URL |
`frame` 结构:
| 字段 | 类型 | 必填 | 说明 |
| --- | --- | --- | --- |
| `firstFrame` | object | 否 | 首帧素材引用 |
| `lastFrame` | object | 否 | 尾帧素材引用 |
`parameters` 支持以下协议字段,但某个模型是否支持以及具体可选值,必须以 `get_model_parameters` 返回结果为准:
| 字段 | 类型 | 说明 |
| --- | --- | --- |
| `count` | integer | 生成数量,最小为 1 |
| `duration` | integer | 视频时长,单位秒、最小为 1,允许值以模型配置为准 |
| `resolutionKey` | string | 分辨率选项 Key |
| `dimensionsKey` | string | 尺寸选项 Key |
| `aspectRatioKey` | string | 宽高比选项 Key |
| `qualityKey` | string | 质量选项 Key |
| `generateAudioKey` | string | 音频生成选项 Key |
| `imageFormatKey` | string | 图片格式选项 Key |
| `videoFormatKey` | string | 视频格式选项 Key |
| `publicVisibilityKey` | string | 公开可见性选项 Key |
#### 最小请求示例
以下模型 ID 仅为示例。即使请求符合 MCP Schema,仍必须满足所选模型的动态参数要求。
```json
{
"jsonrpc": "2.0",
"id": 40,
"method": "tools/call",
"params": {
"name": "submit_generation_task",
"arguments": {
"clientRequestId": "mcp-20260923-000001",
"generationType": "IMAGE",
"modelConfigId": 1001,
"prompt": "A product photograph on a clean studio background"
}
}
}
```
#### 携带参考图的视频生成示例
```json
{
"jsonrpc": "2.0",
"id": 41,
"method": "tools/call",
"params": {
"name": "submit_generation_task",
"arguments": {
"clientRequestId": "mcp-20260923-000002",
"generationType": "VIDEO",
"modelConfigId": 1103,
"prompt": "Slow camera movement, natural lighting",
"imageAssets": [
{
"assetId": 506500001
}
],
"parameters": {
"count": 1,
"duration": 5,
"resolutionKey": "720P",
"aspectRatioKey": "16:9"
}
}
}
}
```
示例中的参数值不代表所有模型都支持。实际调用必须使用 `get_model_parameters` 为 `modelConfigId=1103` 返回的有效值。
#### `structuredContent` 示例
```json
{
"task": {
"taskId": "GT20260923000001",
"taskType": "VIDEO_GENERATION",
"status": "PROCESSING",
"items": [
{
"itemId": "GI20260923000001",
"status": "CREATED"
}
]
}
}
```
#### 幂等与扣分规则
* `clientRequestId` 的幂等范围是当前认证用户。
* 同一个业务请求因网络超时等原因重试时,必须保持相同的 `clientRequestId` 和相同参数。
* 新的业务请求必须生成新的 `clientRequestId`。
* 不要使用同一个 `clientRequestId` 提交不同参数,否则会返回幂等冲突。
* 请求成功进入正式链路后会产生真实积分消耗;调用方不能通过重复请求绕过计费。
### 6.5 `get_generation_task`
查询当前用户某个生成任务的状态、进度、生成结果或失败信息。
#### 输入参数
| 字段 | 类型 | 必填 | 说明 |
| --- | --- | --- | --- |
| `taskId` | string | 是 | `submit_generation_task` 返回的任务 ID,1~64 字符 |
#### 请求示例
```json
{
"jsonrpc": "2.0",
"id": 50,
"method": "tools/call",
"params": {
"name": "get_generation_task",
"arguments": {
"taskId": "GT20260923000001"
}
}
}
```
#### `structuredContent` 示例
```json
{
"task": {
"taskId": "GT20260923000001",
"taskType": "VIDEO_GENERATION",
"status": "SUCCESS",
"progress": 100,
"items": [
{
"itemId": "GI20260923000001",
"status": "SUCCESS",
"progress": 100,
"results": [
{
"assetId": 506500101,
"url": "https://cdn.example.com/result/506500101.mp4",
"thumbnailUrl": "https://cdn.example.com/result/506500101.jpg",
"assetName": "generated-video.mp4"
}
],
"errorCode": null,
"errorMessage": null
}
]
}
}
```
#### 输出字段
| 字段 | 类型 | 说明 |
| --- | --- | --- |
| `task.taskId` | string | 主任务 ID |
| `task.taskType` | string | 任务类型 |
| `task.status` | string | 主任务状态 |
| `task.progress` | integer/null | 主任务进度,0~100 |
| `task.items[].itemId` | string | 任务明细 ID |
| `task.items[].status` | string | 任务明细状态 |
| `task.items[].progress` | integer/null | 明细进度 |
| `task.items[].results` | object\[\] | 已生成并入库的结果素材 |
| `task.items[].results[].assetId` | integer | 结果素材 ID |
| `task.items[].results[].url` | string | 结果素材当前 URL |
| `task.items[].results[].thumbnailUrl` | string/null | 结果缩略图 URL |
| `task.items[].results[].assetName` | string/null | 结果素材名称 |
| `task.items[].errorCode` | string/null | 明细失败码 |
| `task.items[].errorMessage` | string/null | 明细失败原因 |
查询操作只读取任务当前状态,不会因为调用本工具而额外触发一次上游模型轮询。
## 7. 任务状态
主任务可能返回以下状态:
| 状态 | 是否终态 | 说明 |
| --- | --- | --- |
| `CREATED` | 否 | 已创建,等待后续处理 |
| `PROCESSING` | 否 | 正在排队、生成或处理结果 |
| `WAITING_INPUT` | 否 | 等待后续输入;主要用于需要分阶段输入的任务 |
| `PARTIAL_SUCCESS` | 是 | 部分明细成功、部分明细失败 |
| `SUCCESS` | 是 | 全部生成成功 |
| `FAILED` | 是 | 任务失败 |
| `CANCELLED` | 是 | 任务已取消 |
任务明细可能返回 `CREATED`、`PROCESSING`、`SUCCESS`、`FAILED`、`CANCELLED`。
调用方可以在 `CREATED`、`PROCESSING` 或 `WAITING_INPUT` 时继续轮询,在主任务进入终态后停止。建议避免高频轮询;可根据预计生成时长采用不少于 3 秒的轮询间隔,并逐步退避。
## 8. HTTP 与协议错误
身份认证发生在 MCP 工具执行之前。认证失败时不会返回 `result.isError`,而是直接返回非 2xx HTTP 状态和 JSON-RPC 错误:
```json
{
"jsonrpc": "2.0",
"id": null,
"error": {
"code": -32001,
"message": "Authentication failed",
"data": {
"requestId": "01J..."
}
}
}
```
| HTTP 状态 | 常见原因 | 建议处理 |
| --- | --- | --- |
| `400` | `X-Embed-Parent-Origin` 缺失或格式错误 | 检查 Header 值是否为服务端配置的完整 Origin |
| `401` | `Authorization` 缺失、不是 Bearer 格式、Token 无效或过期 | 重新获取三方 Token;不要传 AI Creative 本地 JWT |
| `403` | Origin 未配置、未启用或无权接入 | 联系 AI Creative 服务方确认 Origin 配置 |
| `500` | 服务端配置冲突或内部异常 | 携带 `requestId` 联系服务方排查 |
| `502` / `503` | 三方认证系统或依赖服务暂时不可用 | 保持相同请求参数,稍后重试 |
处理错误时应优先记录并反馈响应中的 `requestId`,不要在日志、报错信息或工单中输出完整 Token。
## 9. Apifox / curl 联调
Apifox 可以直接用于协议和工具联调:
1. 新建 `POST https://aicreative-api-beta.creatiads.com/api/mcp` 请求。
2. 配置第 2 节中的全部必填 Header。
3. Body 选择 JSON,先发送 `tools/list`。
4. 再使用各工具章节中的 `tools/call` 请求体进行测试。
5. 响应可能是普通 JSON,也可能是 `text/event-stream`。Apifox 中看到 `data:` 开头的 SSE 内容属于正常情况。
curl 示例:
```bash
curl --request POST 'https://aicreative-api-beta.creatiads.com/api/mcp' \
--header 'Authorization: Bearer ' \
--header 'X-Embed-Parent-Origin: https://app-beta.creatiads.com' \
--header 'Content-Type: application/json' \
--header 'Accept: application/json, text/event-stream' \
--header 'language: en' \
--data '{"jsonrpc":"2.0","id":1,"method":"tools/list","params":{}}'
```
执行 `submit_generation_task` 前,请先确认当前环境、账号和模型配置允许产生真实积分消耗。
## 10. 接入检查清单
* [ ] 已从 AI Creative 服务方获得 MCP 地址和允许使用的
* [ ] 每个 MCP HTTP 请求都携带三方 Token 和 Origin,而不是只在初始化请求中携带。
* [ ] 能够同时处理 JSON 与 SSE 响应。
* [ ] 检查
* [ ] 使用
* [ ] 使用
* [ ] 使用
* [ ] 正确生成和复用
* [ ] 生成任务按异步方式处理,并在终态停止轮询。
* [ ] 日志会记录