blender-render-studio / docs /API.zh-CN.md
cpuai's picture
Configure GPU Eevee defaults and verify graphics backends across ZeroGPU sizes
d443689 verified
|
Raw History Blame Contribute Delete
12.5 kB
# API、MCP 与 Agent 调用
API 与 UI 共用同一任务实现,不能通过 API 绕开配置、上传、资源或 GPU 时限。启动后点击 Gradio 底部「Use via API」查看当前服务器生成的权威接口说明。任务 ID 是访问凭据,返回的文件 URL 也不应公开。
## 端点约定
使用 `gradio_client.Client.predict(..., api_name="/端点名")` 调用。服务端函数返回 JSON 并不代表业务成功,必须同时检查 `status`、`error`、`remaining_frames`;导出还应检查 `export_complete` / `export_error`。
| API 名称 | 输入顺序 | 返回 |
| --- | --- | --- |
| `/environment_info` | 无 | 环境版本、ZeroGPU 标志、FFmpeg 可用性;不申请 GPU |
| `/config_schema` | 无 | 允许字段、默认值与校验限制的 JSON Schema |
| `/gpu_self_test` | 无 | `(report, files, image)`;真实小场景渲染,GPU 模式必须检查 `gpu_verified` |
| `/prepare_job` | `files`, `config_json`, `config_file` | `(job_id, status)`;`config_file` 可为 null,非空时优先 |
| `/inspect_job` | `job_id` | 状态与 `inspection`,包括场景/相机/`missing_assets` |
| `/render_chunk` | `job_id` | 新状态;最多处理配置中的 `batch_size` 帧 |
| `/job_status` | `job_id` | 当前状态与完成帧列表;不等待 Blender 队列 |
| `/cancel_job` | `job_id` | 请求停止并保留完成帧;不等待 Blender 队列 |
| `/resume_job` | `job_id` | 清除取消标记、验证已完成帧;不会启动渲染 |
| `/finalize_job` | `job_id` | `(summary, files, image, video)`;部分结果也可导出,视频需完整帧 |
`render_chunk` 使用队列并等待当前批次结束;客户端不应把多个批次并行提交。`job_status` 适合进度查看,轮询本身不会推进渲染。`prepare_job` 冻结配置,恢复沿用原配置;需要修改时创建新任务。
## 完整命令行客户端
```bash
python -m pip install "gradio_client>=2.0,<3"
python examples/client_render.py --space YOUR_NAME/YOUR_SPACE --project project.zip --config examples/video.json --output outputs --self-test
```
脚本会上传本地文件、保存 ID、检查资源、串行渲染、检查每批 `error`,再调用导出并把文件复制到 `outputs`。所有进度为 JSON 行,便于 agent 解析。新建任务若发现已有任务文件会停止,避免不小心重复上传渲染。
| 参数 | 含义 |
| --- | --- |
| `--space` | 必需;`用户名/Space名` 或 Gradio 根 URL |
| `--project` | 新任务必需;一个 ZIP 或多个本机文件路径 |
| `--config` | 新任务必需;本机 JSON 配置路径 |
| `--output` | 下载目录,默认 `outputs` |
| `--job-file` | 任务凭据保存位置,默认 `OUTPUT/render-job.json` |
| `--resume-job [ID]` | 有 ID 时恢复它;省略 ID 时从任务文件恢复 |
| `--inspect` / `--inspect-only` | 上传/恢复后只检查,不开始渲染 |
| `--max-batches N` | 本次最多处理 N 批并导出;0 为直到完成 |
| `--self-test` | 先运行真实小场景自检 |
```bash
# 只检查,保留 ID;确认相机/资源后再续渲。
python examples/client_render.py --space YOUR_NAME/YOUR_SPACE --project project.zip --config examples/image.json --output image-result --inspect
# 每次处理最多 5 批,下载阶段性结果。
python examples/client_render.py --space YOUR_NAME/YOUR_SPACE --resume-job --output image-result --max-batches 5
# 多个上传文件:复杂目录结构请优先使用 ZIP。
python examples/client_render.py --space YOUR_NAME/YOUR_SPACE --project scene.blend texture.png --config examples/image.json --output another-result
```
脚本默认把缺失/被阻止的资源视为错误;若 JSON 明确设置 `strict_assets=false`,会输出警告信息并继续,渲染效果可能因此变化。退出码:0 为完成或主动达到批数上限/仅检查;1 为错误;130 为键盘中断。遇到配额和超时不会循环重试。
## 身份验证
私有 Space 以及需要账号身份的调用,先在运行客户端的环境设置 `HF_TOKEN`。令牌须有访问该 Space 的权限。不要将令牌写到场景、JSON、MCP 示例文件或 git 仓库里。脚本从环境读取令牌并兼容新版 `token=` 与旧版 `hf_token=` 构造参数,不打印令牌。
本机 PowerShell 可交互读取并设置令牌:
```powershell
$env:HF_TOKEN = Read-Host "HF Token" -MaskInput
python examples/client_render.py --space YOUR_NAME/YOUR_SPACE --project project.zip --config examples/video.json --output outputs
```
`-MaskInput` 需要 PowerShell 7;其他环境可使用系统环境变量/密码管理器。平台的账号配额、访问和计费规则仍适用。
## Python 最小闭环
以下代码可直接保存执行;将 Space ID 与本机路径改为实际值。部署目录自带客户端提供更完整的恢复、下载与错误处理。
```python
import inspect
import json
import os
from pathlib import Path
from gradio_client import Client, handle_file
space = "YOUR_NAME/YOUR_SPACE"
output = Path("outputs").resolve()
output.mkdir(parents=True, exist_ok=True)
auth_name = "token" if "token" in inspect.signature(Client).parameters else "hf_token"
client = Client(space, download_files=str(output), httpx_kwargs={"timeout": 120},
**{auth_name: os.getenv("HF_TOKEN")})
config = Path("examples/image.json").read_text(encoding="utf-8-sig")
job_id, status = client.predict(
[handle_file("project.zip")], config, None, api_name="/prepare_job"
)
# ID 要立即保存;不要因网络中断直接重复 prepare_job。
(output / "job-id.txt").write_text(job_id, encoding="utf-8")
status = client.predict(job_id, api_name="/inspect_job")
if status.get("error"):
raise RuntimeError(status["error"])
missing = (status.get("inspection") or {}).get("missing_assets") or []
if missing and status.get("config", {}).get("strict_assets", True):
raise RuntimeError(json.dumps(missing, ensure_ascii=False))
while status.get("remaining_frames"):
before = status["completed_count"]
status = client.predict(job_id, api_name="/render_chunk")
print(status["completed_count"], "/", status["total_frames"])
if status.get("error"):
# 先导出完成帧与日志,再终止;不要在配额不足时无限重试。
client.predict(job_id, api_name="/finalize_job")
raise RuntimeError(status["error"])
if status["completed_count"] <= before:
raise RuntimeError("没有完成新帧,停止自动重试。")
summary, files, image, video = client.predict(job_id, api_name="/finalize_job")
if not summary.get("export_complete"):
raise RuntimeError(summary.get("export_error") or "输出未完整生成")
print(json.dumps({"job_id": job_id, "files": files}, ensure_ascii=False))
```
客户端使用 `handle_file` 自动上传;不能直接把本机路径文本当作远端服务器文件。若想上传独立 JSON 文件:
```python
job_id, status = client.predict(
[handle_file("project.zip")],
"{}",
handle_file("examples/video.json"),
api_name="/prepare_job",
)
```
## 常用 JSON 配置字段
以下是本应用字段,与任意 Blender Python 属性不是一一透传关系。未列出的完整字段请查询 `/config_schema`。
| 字段 | 示例 / 范围 | 说明 |
| --- | --- | --- |
| `schema_version` | `1` | 配置协议版本 |
| `blend_file` | `project/scene.blend` 或 null | 主工程的解压根目录相对路径 |
| `mode` | `image` / `frames` / `video` | 单图、帧序列或视频 |
| `scene` / `camera` / `view_layer` | 名称或 null | 指定 Blender 数据块;默认沿用场景设置 |
| `width` / `height` | 16–8192 | 基础分辨率,受像素总量上限限制 |
| `resolution_percentage` | 1–100 | 实际输出缩放比例 |
| `engine` | `EEVEE` / `CYCLES` | 默认 Eevee |
| `samples` | 1–4096 | Eevee 渲染采样数或 Cycles 最大采样数 |
| `denoise` | true / false | 降噪 |
| `adaptive_threshold` | 0.0–1.0 | 自适应采样阈值 |
| `frame` | 正整数 | 单图帧号 |
| `frame_start` / `frame_end` / `frame_step` | 正整数 | 动画帧范围与步长 |
| `fps` | 1–120 | 时间基准;跳帧输出的播放帧率为 `fps/frame_step` |
| `format` | `PNG` / `OPEN_EXR` | 视频模式只接受 PNG |
| `color_depth` | 8 / 16 / 32 | PNG:8/16;EXR:16/32 |
| `transparent` | true / false | 透明背景;MP4 不支持 |
| `device` | `AUTO` / `CUDA` / `OPTIX` / `CPU` | 默认 AUTO;无需管理员切换。AUTO 请求 GPU,CUDA/OPTIX 仅适用 Cycles |
| `batch_size` | 1–64 | 每次请求最多渲染帧数 |
| `gpu_seconds` | 10–600 | ZeroGPU 请求预算;平台可能另有限制,不是时长保证 |
| `cpu_timeout` | 10–7200 | 普通 GPU/CPU 子进程与编码超时 |
| `strict_assets` | true / false | 默认缺失资源拒绝渲染 |
| `video_crf` | 0–40 | 视频质量;通常 18,越小输出越大 |
| `video_preset` | medium / fast / slow | FFmpeg 编码速度/压缩取舍 |
`gpu_seconds` 是当前批次的预算,不是整个动画的预算。应用给子进程预留收尾时间,因此可用于 Blender 的时间略短。普通 GPU/CPU 模式使用 `cpu_timeout`,名称保留用于同一配置协议。
## MCP 接入
本项目通过 `demo.launch(mcp_server=True)` 暴露工具,要求已安装 `gradio[mcp]`。使用 Streamable HTTP:
```json
{
"mcpServers": {
"blender-render": {
"type": "http",
"url": "https://YOUR-SPACE-DOMAIN.hf.space/gradio_api/mcp/"
}
}
}
```
不同 MCP 客户端可能使用 `servers` 代替 `mcpServers`,或自行管理 `Authorization` 头/OAuth;请在客户端的安全凭据设置中添加认证。示例文件不硬编码令牌。工具名以 `tools/list` 实际发现结果为准;某些客户端会自动添加服务名前缀。
MCP 的 JSON 参数不能携带本机文件系统权限。可采用以下方式:
1. Agent 先用 `gradio_client` 或完整示例脚本上传本地文件并执行 `/prepare_job`,取得 job ID;后续全部使用 MCP 的检查、渲染、查询与导出工具。
2. MCP 客户端支持 Gradio 文件上传时,使用其上传功能得到有效文件引用。不能虚构服务器路径或简单传入本机绝对路径。
3. 有可访问的托管文件时,遵循服务器生成的 MCP 文件 schema 和客户端支持的 URL 上传流程。服务器必须可访问该 URL;本应用不提供任意 URL 代理或自定义下载器,也不会替 URL 补上私有存储的认证。
大文件和私有本机文件推荐第一种方式。返回的结果由 Gradio 表达为文件引用/下载地址,MCP 客户端能否自动下载取决于其文件支持能力;Python 客户端已处理鉴权下载。
HF 也提供 Hub MCP 集成;是否能直接添加某个私有 Space、如何传递用户身份,以其客户端及 Hub 当前能力为准。[HF 的 MCP 官方文档](https://huggingface.co/docs/hub/en/spaces-mcp-servers)、[Gradio MCP 指南](https://www.gradio.app/guides/building-mcp-server-with-gradio)
## 推荐 Agent 策略
先读取 `environment_info` 与 `config_schema`;首次部署调用 `gpu_self_test`。准备后立刻保存 ID,检查场景相机和缺失资产,再串行调用 `render_chunk`,每次都判断错误和完成帧增量。全部完成后 `finalize_job` 并核验输出。出现配额、超时或兼容性失败时停止自动重试、取回部分输出和日志,明确报告原因;修复后用相同 ID 恢复,若修改工程或配置则新建任务。
## 1.1.0 默认模式
空配置 `{}` 选择 `engine=EEVEE, device=AUTO`,请求 GPU 图形渲染。CPU 为可选模式,使用 Mesa 软件 OpenGL。`cpu_self_test` 无参数,返回真实 CPU Eevee 自检结果、日志与图片;`gpu_self_test` 明确测试 Cycles GPU。ZeroGPU 不保证提供 Eevee 所需硬件 EGL/OpenGL;Eevee GPU 检测到软件驱动会报错。已有旧任务按 Cycles 续渲,新任务使用新默认。
## 1.1.1 GPU Eevee 检测
`eevee_gpu_self_test(gpu_size="large", graphics_backend="opengl")` 支持 `large` / `xlarge` 与 `opengl` / `vulkan`,返回 `(report, files, image)`;会显式申请一次 GPU,使用 Eevee 实际渲染小场景。`gpu_eevee_usable=true` 表示通过。GPU 计算可用不代表 GPU 图形接口可用,失败保留完整诊断;CPU 渲染不调用此接口;xlarge 消耗两倍配额。
`gpu_size` 默认 `large`,可选 `xlarge`,只影响 ZeroGPU 租约。`graphics_backend` 默认 `opengl`,可选 `vulkan`,只作用于 GPU + Eevee。