跳转到主要内容

Documentation Index

Fetch the complete documentation index at: https://docs.cyberun.cloud/llms.txt

Use this file to discover all available pages before exploring further.

GET /api/v1/r/tasks/{taskId}/events 打开一个 Server-Sent Events 流,每次状态变化或进度更新都会推送一个事件。连接保持开启直到任务 进入终态(completedfailedcancelled),然后关闭。 请优先使用它,而非轮询 GET /r/tasks/{taskId} —— 延迟更低、请求更少。

建立连接

使用 Bearer 令牌(JWT、sk-dk-):
curl -N \
  -H "Authorization: Bearer sk-..." \
  https://core.cyberun.cloud/api/v1/r/tasks/{taskId}/events
浏览器内建的 EventSource 支持自定义请求头,意味着它无法 携带 Authorization 头。服务端运行时(Node fetch、Python requestshttpx)、React Native、以及 eventsource 这类库都 可以正常使用。在浏览器中请通过你自己的后端中转。

事件类型

事件含义
status任务状态变化(例如 pendingwaitingqueuedrunning)。
progress执行进度,包含 progressstep_currentstep_total、当前节点。
completed任务完成。包含输出对象。
failed任务失败。包含错误字符串。
cancelled任务在进入终态前被取消。
error服务端读取任务状态时出错。流可能仍然继续。

status

event: status
data: {"task_id":"...","status":"running","timestamp":"2026-02-01T14:30:05Z"}

progress

event: progress
data: {
  "task_id":"...",
  "progress":0.35,
  "current_node":"3",
  "step_current":7,
  "step_total":20,
  "timestamp":"2026-02-01T14:30:10Z"
}
Nerfstudio 任务额外携带 stagedownloadprocess_datatrainexportupload)以及人类可读的 message 字段。
字段类型含义
progressnumber0.01.0 的整体进度。
step_currentinteger已完成的步数(运行时报告时)。
step_totalinteger本次运行的总步数。
current_nodestring运行时的当前节点标识(ComfyUI 工作流为节点 ID)。
stagestring仅 Nerfstudio。粗粒度阶段名称。
messagestring仅 Nerfstudio。自由格式状态文本。

终态事件

event: completed
data: {"task_id":"...","status":"completed","completed_at":"...","output":{...}}

event: failed
data: {"task_id":"...","status":"failed","error":"ComfyUI execution error: ..."}

event: cancelled
data: {"task_id":"...","status":"cancelled"}
这三种事件之后服务器会关闭连接。

error

event: error
data: {"message":"failed to fetch task status"}
服务端读取任务状态的瞬时问题。视为可恢复 —— 任务本身可能仍在运行。 如果流也关闭,请改为轮询(见下方)。

完整事件流示例

一个典型的 ComfyUI 任务从头到尾:
event: status
data: {"task_id":"...","status":"waiting","timestamp":"..."}

event: status
data: {"task_id":"...","status":"queued","timestamp":"..."}

event: status
data: {"task_id":"...","status":"running","timestamp":"..."}

event: progress
data: {"task_id":"...","progress":0.15,"step_current":3,"step_total":20,"current_node":"3"}

event: progress
data: {"task_id":"...","progress":0.5,"step_current":10,"step_total":20,"current_node":"3"}

event: progress
data: {"task_id":"...","progress":1.0,"step_current":20,"step_total":20,"current_node":"3"}

event: completed
data: {"task_id":"...","status":"completed","output":{...}}

轮询兜底

如果网络无法承载 SSE,或你不想长连接,可改为轮询 GET /r/tasks/{taskId} 直到 task_statuscompletedfailedcancelled 之一。轮询间隔 3 秒是个合理默认值。
curl -s \
  -H "Authorization: Bearer sk-..." \
  https://core.cyberun.cloud/api/v1/r/tasks/{taskId}
当任务为 completed 时,通过 GET /r/tasks/{taskId}/result 获取产物链接。

消费事件流

import json, requests

API_KEY = "sk-..."
BASE = "https://core.cyberun.cloud/api/v1/r"

with requests.get(
    f"{BASE}/tasks/{task_id}/events",
    headers={"Authorization": f"Bearer {API_KEY}"},
    stream=True,
) as stream:
    event_type = None
    for line in stream.iter_lines(decode_unicode=True):
        if not line:
            continue
        if line.startswith("event:"):
            event_type = line[6:].strip()
        elif line.startswith("data:"):
            data = json.loads(line[5:].strip())
            if event_type == "progress":
                pct = int(data["progress"] * 100)
                print(f"{pct}% ({data['step_current']}/{data['step_total']})")
            elif event_type in ("completed", "failed", "cancelled"):
                print(event_type, data)
                break

相关