3 changed files with 141 additions and 2 deletions
@ -0,0 +1,129 @@ |
|||
# popiartServer Stable Media URL V1 |
|||
|
|||
这份文档只描述 `popiartServer` 这一层为了支持稳定媒体 URL 所做的职责扩展,不覆盖 `popiartcli` 的命令面,也不要求修改 `PopiNewAPI` 的现有通道实现。 |
|||
|
|||
## 背景 |
|||
|
|||
原有本地开发版 `popiartServer` 更偏向: |
|||
|
|||
- `artifact` read-through |
|||
- `result_refs_json` 存 `data_url` 或上游临时 `url` |
|||
- `GET /artifacts/:id/content` 由 server 当场去解码或代理下载 |
|||
|
|||
这种实现能跑通基本流程,但不适合多模态 skill 的复用: |
|||
|
|||
- `img2img` 经常还要重新拉流或转 base64 |
|||
- 上游签名 URL 可能过期 |
|||
- 前一个 job 的输出不能稳定地作为下一个 job 的 URL 输入 |
|||
|
|||
## V1 目标 |
|||
|
|||
`popiartServer` 在不依赖外部对象存储的前提下,先提供一套本地可运行的稳定媒体 URL 能力: |
|||
|
|||
- 本地上传文件可立即获得稳定 URL |
|||
- 新生成的 job 结果会被 re-host 到本地 media store |
|||
- 新 artifact 会携带 `media_id` 和 `url` |
|||
- `image2video` 的 `vidu*` 路由可以直接复用 artifact URL |
|||
|
|||
## 新接口 |
|||
|
|||
### `POST /v1/media/upload` |
|||
|
|||
上传一个本地文件,直接创建 media 记录并返回: |
|||
|
|||
- `id` |
|||
- `project_id` |
|||
- `filename` |
|||
- `content_type` |
|||
- `size_bytes` |
|||
- `created_at` |
|||
- `url` |
|||
- `visibility` |
|||
- `sha256` |
|||
|
|||
### `GET /v1/media/:id` |
|||
|
|||
读取 media 元数据。这个接口需要登录态,并要求 media 属于当前用户。 |
|||
|
|||
### `GET /v1/media/:id/content` |
|||
|
|||
读取稳定内容 URL。这个接口默认允许匿名 GET,以便模型提供商可以直接 fetch。 |
|||
|
|||
## Artifact 行为变化 |
|||
|
|||
`POST /v1/artifacts/upload` 现在不再只把内容塞成 `data_url`: |
|||
|
|||
1. server 先把上传文件写入本地 media store |
|||
2. 再创建本地 upload job |
|||
3. 最终 artifact 返回: |
|||
- `id` |
|||
- `media_id` |
|||
- `url` |
|||
- `visibility` |
|||
- `sha256` |
|||
- `storage_status` |
|||
|
|||
## Job 结果行为变化 |
|||
|
|||
对于新的 `text2image`、`img2img`、`image2video` 结果: |
|||
|
|||
1. 先从 `PopiNewAPI` 或上游临时结果读出真实内容 |
|||
2. re-host 到 `POPIART_DATA_DIR/media/` |
|||
3. 把 `local_path + media_id + stable url` 写回 `result_refs_json` |
|||
|
|||
这样新的 artifact 不再依赖上游临时 URL。 |
|||
|
|||
## 本地 media store |
|||
|
|||
V1 的本地开发版不引入 S3/R2/OSS,而是用本地文件系统: |
|||
|
|||
- blob 文件:`POPIART_DATA_DIR/media/blobs/` |
|||
- metadata JSON:`POPIART_DATA_DIR/media/meta/` |
|||
|
|||
如果 `POPIART_DATA_DIR` 没显式配置,但 `POPIART_SQLITE_PATH` 已配置,则 `DataDir` 会自动落到 SQLite 所在目录,避免测试把 media 文件写进源码目录。 |
|||
|
|||
## 当前已打通的 URL 复用 |
|||
|
|||
### Artifact / media |
|||
|
|||
- `media upload` -> stable URL |
|||
- `artifact upload` -> stable URL |
|||
- 新 `artifact` 的 `GET /artifacts/:id` -> `url` |
|||
|
|||
### Runtime output |
|||
|
|||
- `text2image` 输出会 re-host |
|||
- `img2img` 输出会 re-host |
|||
- `image2video` 输出会 re-host |
|||
|
|||
### URL-first dispatch |
|||
|
|||
当前已优先 URL 化的路径是: |
|||
|
|||
- `video.image2video` |
|||
- 当模型 ID 以 `vidu` 开头,且 reference 已有 stable URL 时,server 会优先用 JSON `images` 传给 `/v1/videos` |
|||
|
|||
这是为了先覆盖当前测试环境最常用的 `viduq2-pro-fast` 路由。 |
|||
|
|||
## 兼容策略 |
|||
|
|||
旧数据仍然兼容: |
|||
|
|||
- 如果 `result_ref.kind == data_url`,继续解码读取 |
|||
- 如果 `result_ref.kind == url`,继续代理下载 |
|||
- 如果 `result_ref.kind == local_path`,优先从本地 media store 读取 |
|||
|
|||
也就是说: |
|||
|
|||
- 历史 artifact 不会立即失效 |
|||
- 新 artifact 才开始享受稳定 URL |
|||
|
|||
## 后续阶段 |
|||
|
|||
后续如果要走生产化路线,可以保持接口不变,只把存储实现替换成对象存储: |
|||
|
|||
- 本地 `media/blobs/` -> S3 / R2 / OSS / COS |
|||
- metadata JSON -> 独立 media table 或对象存储元数据 |
|||
- `GET /v1/media/:id/content` -> CDN / 受控稳定 URL |
|||
|
|||
但这一步不是 V1 本地开发验证的前置条件。 |
|||
Loading…
Reference in new issue