Skip to content

Seedance

Seedance 是字节跳动的视频生成系列,由火山引擎方舟渠道提供。RouteAPI 会把你的请求转换成方舟的 /api/v3/contents/generations/tasks 调用,因此每个任务都和其他视频模型一样走提交、轮询、下载的流程——见创建任务和查询任务。本页说明 Seedance 适配器读取哪些字段、各模型的限制、如何读取 Seedance 任务记录,以及费用如何计算。

视频生成是异步任务:提交后保存 task_id,每 10–15 秒轮询一次,状态变成 SUCCESS 后下载。4 秒 480p 的视频通常需要 1–5 分钟;分辨率越高、时长越长,耗时越久。

模型 ID方舟模型分辨率时长说明
seedance-2.5doubao-seedance-2-5-260628480p / 720p / 1080p4–30 秒支持草稿预览、参考/编辑/扩展模式和 mov 输出
seedance-2.0doubao-seedance-2-0-260128480p / 720p / 1080p / 4k4–15 秒支持图像、视频和音频参考素材
seedance-2.0-fastdoubao-seedance-2-0-fast-260128480p / 720p4–15 秒更快、更便宜的 2.0 变体
seedance-2.0-minidoubao-seedance-2-0-mini-260615480p / 720p4–15 秒低成本的 2.0 变体

请发送 GET /v1/models 返回的模型 ID。提供这些模型的渠道会把它映射到第二列对应的方舟模型名,这也是适配器同时接受两种命名的原因。你的账户能用哪些模型、单价是多少,以 RouteAPI 控制台为准。

分辨率和时长两列是字节对各模型的规定范围。RouteAPI 不校验这些范围:我们这边唯一的时长校验是「顶层 duration / seconds 必须落在 0–3600」这条通用规则(见限制与错误)。其余全部由方舟执行——在 2.0 模型上请求 30 秒、使用不支持的分辨率或参考素材数量超限,请求都会先提交,再由方舟拒绝,表现为 fail_to_fetch_task,附带方舟的状态码和消息。RouteAPI 也不会为缺失的 resolution 或 duration 补默认值,默认值由方舟决定;这种情况下费用估算按 1080p 和 5 秒计算,所以预扣金额只是估算,不是方舟的默认值。

Seedance 1.x(doubao-seedance-1-0-*、doubao-seedance-1-5-*)已下线。映射到 1.x 名称的请求会在模型映射之后、预扣或发往上游之前被拒绝,返回 400 和错误码 model_not_supported。

信封字段Seedance 适配器的处理
prompt作为末尾的 text 项追加,除非 metadata.content 已包含 text 项,或 content 是 2.5 的 draft_task。每个请求都必须有
images / image每张图生成一个不带 role 的 image_url 内容项。存在 metadata.content 时被忽略
ratio作为方舟的 ratio 发送
resolution作为方舟的 resolution 发送
duration作为方舟的 duration 发送;能解析为正整数的顶层 seconds 会覆盖它
generate_audio作为 generate_audio 发送;显式 false 也会转发
metadata解析进强类型结构,其中的值优先于顶层同名字段

size、input_reference 和 mode 属于通用信封,但 Seedance 适配器不读取它们:请改用 resolution / ratio,以及 images 或 content。

metadata 的类型会在提交前校验:类型错误(content 传对象、image_url 传裸字符串、duration: "abc")返回 400 且不扣费,消息以 unmarshal metadata failed 开头。metadata 里的数值和布尔字段也接受字符串形式("duration": "6"、"watermark": "false");顶层的标量字段必须使用各自的 JSON 类型。

以下字段从请求体顶层读取,因此用与其他供应商相同的结构发送即可,不必包进 metadata:

字段类型说明
ratiostring宽高比:16:9、4:3、1:1、3:4、9:16、21:9 或 adaptive
resolutionstring480p、720p、1080p 或 4k,视模型而定
durationinteger时长(秒)。0 视为「未设置」不会发送;需要显式转发 0 时请改用 metadata
generate_audioboolean是否生成配乐;false 会被显式转发
secondsstring时长的旧式字符串形式;能解析为正整数时同时覆盖 duration 和 metadata.duration。非数字值会被忽略
字段类型说明
contentarray输入素材,取代 images;见 metadata.content
ratio、resolution、duration、generate_audio与顶层相同优先于顶层值。正的顶层 seconds 仍然优先于最终的 duration
seedinteger随机种子;0 会作为显式值转发
framesinteger帧数。设置后费用估算用它代替时长,方舟也用它代替时长
camera_fixedboolean保持镜头固定
watermarkboolean在输出上加供应商侧水印。字节文档说明默认 false
return_last_frameboolean同时以图像形式返回最后一帧
service_tierstring供应商服务等级,例如 default。原样透传
execution_expires_afterinteger任务过期秒数。字节文档给出的范围是 3600–259200,默认 172800,由方舟执行
priorityinteger供应商侧队列优先级,0–9,数值越大越先执行。方舟只在你自己账户内排序任务
safety_identifierstring你的终端用户标识,最长 64 个字符。转发给方舟,由方舟校验长度
draftbooleanSeedance 2.5 草稿预览——见草稿预览
output_formatstring输出容器,原样转发。Seedance 2.5 接受 mp4(默认)或 mov
omni_reference_task_typestringSeedance 2.5 参考模式,原样转发:auto、reference、edit 或 extend

callback_url 不会被转发,也不会发送回调——请轮询结果。tools 同样会被丢弃;此 API 不提供上游联网搜索。包括这两者在内的无法识别的键不会报错,只是被忽略。metadata.model 不会被读取:请求体的 model 始终是渠道的上游模型名。

content 是按顺序排列的输入项数组。每一项有一个 type、对应的载荷字段,以及可选的 role:

type载荷role 取值
texttext—
image_urlimage_url.urlfirst_frame、last_frame、reference_image
video_urlvideo_url.urlreference_video
audio_urlaudio_url.urlreference_audio
draft_taskdraft_task.id—

RouteAPI 只校验项的结构(载荷类型错误返回 400),不校验 role 名称;未知 role 会被转发,由方舟决定是否拒绝。URL 可以是公网 http(s) 链接、图像和音频的 data: URI,或 asset://<asset_id> 引用——上传素材以及引用真人图像(必须来自已验证的素材组)的方法见素材。

由转换过程带来的规则:

  • 如果存在 content,它会原样使用;顶层 images 会被忽略而不是合并。空 content 数组视为未提供,顶层 images 仍然生效。
  • 如果 content 中没有 text 项,顶层的 prompt 会作为末尾文本项追加。唯一例外是 content 为 draft_task 的 2.5 请求:不会追加 prompt,但请求体中仍必须存在 prompt。
  • 在 prompt 中按序号引用素材(“image 1”“video 1”),按 content 顺序分类型计数。
  • 首帧、首尾帧和多模态参考是三种不同模式。除非你已确认模型接受该组合,否则不要混用。

下面的参考素材限制由方舟执行,不是 RouteAPI 的校验:超限请求会先提交,再由上游拒绝。

项目Seedance 2.52.0 系列
参考图数量1–301–9
参考视频最多 10 段,总时长 ≤30 秒最多 3 段,总时长 ≤15 秒
参考音频最多 10 段,总时长 ≤30 秒最多 3 段,总时长 ≤15 秒,且必须同时有图片或视频
单张图片小于 30MB,宽高 300–6000 像素同左
单段视频mp4 / mov,小于 200MB同左
单段音频wav / mp3,小于 15MB同左

Seedance 2.x 拒绝含真实人脸的参考图和参考视频。需要用真人肖像时,先完成真人核验,再用 asset:// 引用已核验的素材——素材 介绍了核验会话、已核验的素材组以及请求规则。

Terminal window
curl https://api.routeapi.ai/v1/video/generations \
-H "Authorization: Bearer $ROUTEAPI_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "seedance-2.0-fast",
"prompt": "A paper boat drifting down a rain-soaked street, cinematic lighting",
"ratio": "16:9",
"resolution": "720p",
"duration": 5,
"generate_audio": false
}'

images 中的单张图像会成为一个不带 role 的图像项,Seedance 将其视为首帧:

Terminal window
curl https://api.routeapi.ai/v1/video/generations \
-H "Authorization: Bearer $ROUTEAPI_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "seedance-2.0",
"prompt": "The camera slowly pushes in as the person looks up and smiles",
"images": ["https://cdn.example.com/first.jpg"],
"ratio": "adaptive",
"resolution": "720p",
"duration": 5
}'

要显式控制首帧/尾帧,请使用 content 并把 prompt 写在其中:

Terminal window
curl https://api.routeapi.ai/v1/video/generations \
-H "Authorization: Bearer $ROUTEAPI_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "seedance-2.0",
"prompt": "The bud slowly opens into a full bloom",
"metadata": {
"content": [
{ "type": "text", "text": "The bud slowly opens into a full bloom" },
{ "type": "image_url", "image_url": { "url": "https://cdn.example.com/bud.jpg" }, "role": "first_frame" },
{ "type": "image_url", "image_url": { "url": "https://cdn.example.com/flower.jpg" }, "role": "last_frame" }
],
"ratio": "adaptive",
"resolution": "720p",
"duration": 5
}
}'

参考图像、视频和音频用 reference_* 系列 role 混在同一个 content 数组中。按类型编号,序号按 content 顺序计算,并在 prompt 中这样引用:

Terminal window
curl https://api.routeapi.ai/v1/video/generations \
-H "Authorization: Bearer $ROUTEAPI_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "seedance-2.0",
"prompt": "The person in image 1 dances following the moves in video 1, with audio 1 as background music",
"metadata": {
"content": [
{ "type": "text", "text": "The person in image 1 dances following the moves in video 1, with audio 1 as background music" },
{ "type": "image_url", "image_url": { "url": "https://cdn.example.com/person.jpg" }, "role": "reference_image" },
{ "type": "video_url", "video_url": { "url": "https://cdn.example.com/dance.mp4" }, "role": "reference_video" },
{ "type": "audio_url", "audio_url": { "url": "https://cdn.example.com/bgm.mp3" }, "role": "reference_audio" }
],
"ratio": "16:9",
"resolution": "720p",
"duration": 10
}
}'

包含视频输入的请求按该模型的视频输入价格计费——见计费。参考素材的数量、时长和格式由方舟执行,见 metadata.content 下的限制表。

Seedance 2.5 增加了模式选择和容器选择。两者对所有 Seedance 模型都会原样转发,是否接受由方舟决定:

Terminal window
curl https://api.routeapi.ai/v1/video/generations \
-H "Authorization: Bearer $ROUTEAPI_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "seedance-2.5",
"prompt": "Continue the scene as the camera pulls back over the harbour",
"metadata": {
"omni_reference_task_type": "extend",
"output_format": "mov",
"content": [
{ "type": "text", "text": "Continue the scene as the camera pulls back over the harbour" },
{ "type": "video_url", "video_url": { "url": "https://cdn.example.com/scene.mp4" }, "role": "reference_video" }
],
"ratio": "16:9",
"duration": 8
}
}'

omni_reference_task_type 取 auto(默认)、reference、edit 或 extend。每种模式期望的输入组合由字节的接口约定决定,RouteAPI 只负责转发该值。

草稿是一种低成本的预览。用它生成最终视频是第二个任务,单独计费。

  1. 提交带 "metadata": { "draft": true, ... } 的请求,等待 SUCCESS。
  2. 从任务记录中读取上游任务 ID:GET /v1/video/generations/{task_id} → data.data.id。
  3. 提交一个新任务,其 content 是单个 draft_task。

第一步:

Terminal window
curl https://api.routeapi.ai/v1/video/generations \
-H "Authorization: Bearer $ROUTEAPI_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "seedance-2.5",
"prompt": "An astronaut walks slowly on the moon",
"metadata": { "draft": true, "duration": 5, "ratio": "16:9" }
}'

第二步,等草稿任务变为 SUCCESS 后执行。data.data.id 是方舟任务 ID,不是外层的 data.task_id:

Terminal window
curl -s https://api.routeapi.ai/v1/video/generations/task_G2RdWGt4t1nck5fYqTjwREKJo8Ze4RAV \
-H "Authorization: Bearer $ROUTEAPI_KEY" | jq -r .data.data.id

第三步:

Terminal window
curl https://api.routeapi.ai/v1/video/generations \
-H "Authorization: Bearer $ROUTEAPI_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "seedance-2.5",
"prompt": "x",
"metadata": {
"content": [ { "type": "draft_task", "draft_task": { "id": "cgt-xxxxxxxx" } } ],
"resolution": "1080p",
"duration": 5
}
}'

prompt 仍然必填;这种形式下它不会作为文本发送,因此任何非空占位符都可以。未显式给 duration 的草稿续作会按模型自动时长上限(2.5 为 30 秒,2.0 为 15 秒)预扣,再按实际用量结算。

草稿 ID 归方舟所有。字节文档说明有效期为 7 天;RouteAPI 不校验,过期的草稿 ID 会由上游报错。

Terminal window
curl https://api.routeapi.ai/v1/video/generations/task_G2RdWGt4t1nck5fYqTjwREKJo8Ze4RAV \
-H "Authorization: Bearer $ROUTEAPI_KEY"
{
"code": "success",
"message": "",
"data": {
"id": 4512,
"created_at": 1792048450,
"updated_at": 1792048569,
"task_id": "task_G2RdWGt4t1nck5fYqTjwREKJo8Ze4RAV",
"platform": "54",
"user_id": 1024,
"group": "default",
"channel_id": 18,
"quota": 108900,
"action": "generate",
"status": "SUCCESS",
"progress": "100%",
"fail_reason": "",
"result_url": "https://ark-content.example/xxxx.mp4",
"submit_time": 1792048458,
"start_time": 1792048461,
"finish_time": 1792048569,
"properties": {
"input": "{\"model\":\"doubao-seedance-2-0-fast-260128\",\"content\":[{\"type\":\"text\",\"text\":\"An orange cat stretching on a windowsill at sunrise\"}],\"generate_audio\":false,\"resolution\":\"720p\",\"ratio\":\"16:9\",\"duration\":5}",
"origin_model_name": "seedance-2.0-fast",
"upstream_model_name": "doubao-seedance-2-0-fast-260128"
},
"data": {
"id": "cgt-20261023100444-9kz46",
"model": "doubao-seedance-2-0-fast-260128",
"status": "succeeded",
"content": { "video_url": "https://ark-content.example/xxxx.mp4" },
"seed": 8202,
"resolution": "720p",
"duration": 5,
"ratio": "16:9",
"framespersecond": 24,
"usage": { "completion_tokens": 108900, "total_tokens": 108900 },
"created_at": 1792048458,
"updated_at": 1792048569
}
}
}

外层字段由 RouteAPI 生成,查询任务 有完整说明。对 Seedance 来说主要看 data.status、data.progress、data.result_url、data.fail_reason 和 data.quota——quota 是当前已扣金额,任务成功后即为结算后的金额。data.properties.input 是 RouteAPI 实际发给方舟的 JSON 快照(超过 512 字节的媒体 URL 会被替换为 [omitted, N bytes]),是确认请求是否真的按你想要的档位发出的最快方式。data.platform 是渠道类型:豆包视频渠道为 54,火山引擎渠道为 45。

data.data 是方舟返回的任务原文,按原样存储,任务结束前可能不完整。如果渠道的上游通过网关信封({"code": 200, "data": {...}})返回,下列字段会再深一层,位于 data.data.data——判断是否结束要看 data.status,而不是某个字段是否存在。值得读取的字段:

字段含义
data.data.id方舟任务 ID,与外层 data.task_id 不同。2.5 草稿正式生成时用它
data.data.content.video_url方舟返回的视频地址,与外层 data.result_url 相同
data.data.content.last_frame_url尾帧图片。仅在开启 return_last_frame 时存在;RouteAPI 只原样存储这段载荷,仅从中解析 content.video_url
data.data.duration / resolution / ratio / framespersecond / seed实际生成参数
data.data.usage.completion_tokens / total_tokens方舟计量的 token 数;total_tokens 是结算用量
data.data.error失败时方舟的错误码和信息

方舟状态到任务记录的映射如下;RouteAPI 不认识的状态按「仍在运行」处理:

方舟 status任务记录状态进度
pending、queuedQUEUED10%
processing、runningIN_PROGRESS50%
succeededSUCCESS100%
failed、expired、cancelledFAILURE100%
其他IN_PROGRESS30%

如果方舟返回 succeeded 但还没有 video_url,RouteAPI 会保持 IN_PROGRESS 继续轮询,而不是结算一个没有结果的任务。任务 FAILURE 时,fail_reason 是方舟的错误信息,缺失时回落为 task failed;没有 error 对象的 expired 或 cancelled 任务分别报告 task expired 和 task cancelled。如果 RouteAPI 自己的任务超时(默认 24 小时)先触发,状态同样是 FAILURE 并带平台文案,两种情况都会退还预扣额度。

data.result_url 是方舟自己的地址,方舟会按自己的计划让它过期(字节文档提到的时长约为 24 小时)——请尽快下载。RouteAPI 的内容端点在调用时重新取用已保存的地址,可以省去你自行跟踪即将过期的链接,但无法让已过期的地址重新可用:

Terminal window
curl -L -o out.mp4 \
https://api.routeapi.ai/v1/videos/task_G2RdWGt4t1nck5fYqTjwREKJo8Ze4RAV/content \
-H "Authorization: Bearer $ROUTEAPI_KEY"

内容端点只提供调用者自己已成功的任务:未完成的任务返回 400 并说明当前状态,未知或他人的 task_id 返回 404,向方舟取文件失败返回 502。它的错误使用 {"error": {"message": "...", "type": "..."}} 结构,没有 code 字段。如果开启了 return_last_frame,data.data.content.last_frame_url 也按方舟的过期时间失效——请一并下载。

Seedance 模型按 token 计费,而不是按请求或按秒。控制台单价是某个分辨率档每百万输出 token 的价格;带视频输入的请求按该模型的视频输入价格计费。

提交时,RouteAPI 根据请求的分辨率和帧数估算输出 token:

frames = 24 × duration + 1 (frames replaces duration when metadata.frames is set)
tokens = pixels × frames / 1024
pixels = 480p: 864×496, 720p: 1280×720, 1080p: 1920×1080, 4k: 3840×2160

时长省略时默认 5 秒;content 为 draft_task 且未显式给时长时,默认到模型的自动时长上限(2.5 为 30 秒,2.0 为 15 秒)。分辨率省略或无法识别时按 1080p 估算。字节的「自动时长」(-1)在顶层会被 0–3600 校验拒绝;以字符串 "-1" 写在 metadata 里则会转发,估算同样按自动时长上限计算。估算值乘以模型倍率、分组倍率和视频输入倍率后作为预扣金额。对于按倍率而非固定价格计费的模型,该估算值会与常规预扣金额比较,取较大者预扣。任务完成时的 token 结算只在模型配置了倍率时执行;模型没有倍率时预扣金额即为最终扣费(如果一个模型既没有倍率也没有固定价格,除非你的账户允许未配置倍率的模型,否则请求会被拒绝)。

请求提交时预扣成功后
给了 duration估算 token 数 × 单价方舟 usage.total_tokens × 单价,差额补扣或退回
未给 duration估算按 5 秒同样的结算
设置了 metadata.frames估算使用帧数同样的结算
draft_task 且无 duration估算按 30 秒 / 15 秒同样的结算
配置了按任务固定价格固定价不变,不做 token 结算
SUCCESS 但没有 usage—保持预扣金额
FAILURE、expired、cancelled—退回预扣额度
400不预扣不扣费

每 token 价格取决于输出分辨率档、请求是否包含视频输入,以及在价格表中定义了该维度的模型上是否生成音频。模型价格表生效且算出的倍率不为 1.0 时,提交响应的 X-New-Api-Other-Ratios 头会以 video_input 项返回该倍率。内置兜底价格表为 2.0 模型登记了 base(480p / 720p)、1080p 和 4k 档,并为每档登记视频输入价格;快速版只有 base 档,视频输入倍率为 22/37。seedance-2.5 和 seedance-2.0-mini 没有内置价格表,分档价格来自控制台配置。渠道也可以用按你所请求模型 ID 配置的 VideoPrice 表覆盖倍率。以控制台显示的模型价格与分档为准。

算例(价格均为假设,真实价格以控制台为准)。假设 seedance-2.0-fast 在 720p 档为 每百万输出 token $2,分组倍率为 1:

  1. 以 720p、duration: 5 提交。估算:1280 × 720 = 921,600 像素,24 × 5 + 1 = 121 帧,921,600 × 121 / 1024 = 108,900 token,预扣 $0.2178。
  2. 方舟回报 usage.total_tokens: 105000,结算金额为 $0.21,退回 $0.0078。
  3. 如果同一请求包含 reference_video 项,内置快速版价格表会给估算值和结算值都乘上 22/37 ≈ 0.5946 的视频输入倍率:预扣约 $0.1295,结算约 $0.1249。

余额或 Key 额度不足以覆盖预扣金额的请求会在发往上游之前被拒绝:钱包不足返回 403 insufficient_user_quota,Key 额度不足返回 403 pre_consume_token_quota_failed。

状态码错误码含义
400invalid_requestprompt 缺失或为空、JSON 格式错误,或 metadata 字段类型错误
400invalid_seconds顶层 duration / seconds 或数值型 metadata.duration 为负或大于 3600
400model_not_supported请求映射到已下线的 Seedance 1.x 模型
400task_not_existtask_id 未知或属于其他账户
403insufficient_user_quota、pre_consume_token_quota_failed钱包余额或 Key 额度不足以覆盖预扣金额
429—上游容量耗尽;消息会被替换为 Upstream load is saturated, please try again later
500build_request_failed、do_request_failed、invalid_response转换失败、上游不可达,或方舟没有返回任务 ID
500get_channel_failed转发阶段选择渠道失败(例如请求过程中渠道记录被删除)
503get_channel_failed渠道在上游遇到凭证或计费硬故障,细节被隐藏
上游状态码fail_to_fetch_task方舟拒绝了提交;HTTP 状态码和消息即方舟的

常见的 400 消息,与实际返回一致:

message原因
prompt is requiredprompt 缺失、为空或只有空白
seconds must be between 1 and 3600顶层 duration / seconds 或数值型 metadata.duration 为负或过大
unmarshal metadata failed: ...metadata 字段类型错误,消息后半段会指出具体字段
model <id> is not supported by this channel原始或上游模型名匹配已下线的 Seedance 1.x 模型
task_not_exist任务 ID 未知或属于其他账户

提交之后发生的失败(内容审核、供应商超时、取消)不会表现为 HTTP 错误。它们会以 FAILURE 连同 fail_reason 出现在任务记录中,预扣金额会被退回。expired 和 cancelled 也按同样方式报告。

  • 接口地址不同。RouteAPI 不提供 /api/v3/contents/generations/tasks,把火山 SDK 的 Base URL 指过来无法使用。
  • 方舟专有参数放在 metadata 里;通用字段(prompt、images、ratio、resolution、duration、generate_audio)也可以写在顶层,由 RouteAPI 映射。
  • 返回的 task_id 是 RouteAPI 的 ID,不是方舟的。方舟的 ID 在任务记录的 data.data.id。
  • 你发送的是目录模型 ID,渠道负责映射到方舟模型名,因此你不需要直接使用方舟的 endpoint ID(ep-...)。
  • 不支持任务列表、取消任务、回调通知和联网搜索;callback_url 和 tools 会被丢弃。
  • 计费按控制台价格表以 token 结算,不采用方舟自身的计费方式。

需要 bash、curl 和 jq。

#!/usr/bin/env bash
set -euo pipefail
: "${ROUTEAPI_KEY:?set ROUTEAPI_KEY first}"
BASE="${ROUTEAPI_BASE:-https://api.routeapi.ai}"
AUTH="Authorization: Bearer $ROUTEAPI_KEY"
TASK_ID=$(curl -sS -X POST "$BASE/v1/video/generations" \
-H "$AUTH" -H "Content-Type: application/json" \
-d '{"model":"seedance-2.0-fast","prompt":"An orange cat stretching on a windowsill at sunrise","duration":5,"resolution":"720p","ratio":"16:9","generate_audio":false}' \
| jq -er .task_id)
echo "task: $TASK_ID"
for _ in $(seq 1 60); do
RESP=$(curl -sS "$BASE/v1/video/generations/$TASK_ID" -H "$AUTH")
STATUS=$(printf '%s' "$RESP" | jq -r .data.status)
echo "status: $STATUS $(printf '%s' "$RESP" | jq -r .data.progress)"
case "$STATUS" in
SUCCESS)
curl -sSL -o "$TASK_ID.mp4" "$BASE/v1/videos/$TASK_ID/content" -H "$AUTH"
echo "saved: $TASK_ID.mp4"
exit 0
;;
FAILURE)
echo "failed: $(printf '%s' "$RESP" | jq -r .data.fail_reason)"
exit 1
;;
esac
sleep 15
done
echo "timed out waiting for the task"
exit 1

循环等待 15 分钟;长任务或高分辨率任务可以调大次数。