外观
Webhook 与安全
约 946 字大约 3 分钟
Open API 的生成任务是异步执行的。平台计划在任务到达终态时向开发者控制台登记的 WEBHOOK_URL 发送事件;调用方必须先验签,再写入业务状态。Webhook 是补充通知,查询任务接口仍是最终一致性的权威来源。
规划中
事件合同
目标事件类型:
| 事件 | 触发条件 | 调用方动作 |
|---|---|---|
video.generation.succeeded | 视频任务成功并生成结果资产。 | 保存资产 ID,处理带有效期的结果地址。 |
video.generation.failed | 视频任务失败。 | 保存错误码与任务 ID,执行可控重试或人工处理。 |
video.generation.cancelled | 任务进入取消终态。 | 更新本地任务与计费展示。 |
目标事件体:
{
"event_id": "EVENT_ID",
"type": "video.generation.succeeded",
"created_at": "2026-08-29T00:00:00Z",
"request_id": "REQUEST_UUID",
"data": {
"task_id": "TASK_ID",
"status": "succeeded",
"result_assets": [
{ "asset_id": "ASSET_ID", "type": "video", "url": "SIGNED_RESULT_URL" }
]
}
}目标签名算法
开发者控制台为每个 Webhook 配置生成独立的 WEBHOOK_SECRET。发送端使用原始请求体计算 HMAC-SHA256,并携带以下头:
X-FrameAI-Event-Id: EVENT_ID
X-FrameAI-Timestamp: UNIX_SECONDS
X-FrameAI-Signature: v1=HEX_HMAC_SHA256签名的目标输入为:
UNIX_SECONDS + "." + RAW_REQUEST_BODY调用方验签步骤:
- 读取原始字节请求体,未完成验签前不要先反序列化后再重新序列化。
- 拒绝超过容忍时间窗的
X-FrameAI-Timestamp,建议窗口为 5 分钟。 - 用
WEBHOOK_SECRET计算相同输入的 HMAC-SHA256,并以常量时间比较签名。 - 使用
X-FrameAI-Event-Id去重;相同事件重复投递时返回成功,不重复创建业务记录。 - 验签通过后将事件与
request_id、task_id一起持久化,再异步处理耗时业务。
重试与响应
| 条件 | 平台目标行为 | 接收端要求 |
|---|---|---|
接收端返回 2xx | 认为投递成功。 | 快速确认后异步处理。 |
超时、网络错误、5xx | 按退避策略重试,并保持同一事件 ID。 | 保证重复事件幂等。 |
4xx | 记录投递失败并按配置决定是否停止重试。 | 仅在确实无法处理时返回 4xx,不要把暂时性错误伪装为成功。 |
| 无回调或回调异常 | 调用方继续使用 GET /tasks/{task_id} 补偿。 | 以任务查询作为最终核对。 |
API 密钥与调用安全
- 每个 API 密钥绑定一个开发者应用、工作空间、环境和最小作用域;禁止团队共用“万能密钥”。
- 密钥只部署在服务端密钥管理系统,通过环境注入或受控密钥代理读取;浏览器、Electron 渲染层、移动端包和 Git 仓库都不能保存生产密钥。
- 密钥创建后仅显示一次。发现泄露、人员变动或调用异常时,先创建替代密钥,完成灰度切换后撤销旧密钥。
- 对每个应用启用 IP 允许列表、调用速率、每日额度与失败率告警;生产和沙箱环境必须使用独立凭据。
- 日志中只保存脱敏密钥前缀、
request_id、任务 ID、状态码和错误码,不记录完整Authorization、回调密钥或用户上传内容。
回调端点验收清单
继续阅读:平台实现清单。