{"record":{"id":"887c2bbe4278ab13","repo":"Comfy-Org/ComfyUI","slug":"kling-3-0-turbo-task-finished-without-a-video-outp","errorCode":null,"errorMessage":"Kling 3.0 Turbo task finished without a video output: {response.model_dump()}","messagePattern":"Kling 3\\.0 Turbo task finished without a video output: (.+?)","errorType":"exception","errorClass":"RuntimeError","httpStatus":null,"severity":"error","filePath":"comfy_api_nodes/nodes_kling.py","lineNumber":2216,"sourceCode":"            response_model=TaskStatusResponse,\n            status_extractor=lambda r: (r.data.task_status if r.data else None),\n        )\n        return IO.NodeOutput(await download_url_to_video_output(final_response.data.task_result.videos[0].url))\n\n\ndef build_turbo_shot_prompt(multi_prompt: list[MultiPromptEntry]) -> str:\n    \"\"\"Render storyboard entries into the Turbo multi-shot prompt 'shot n, m, words; ...'.\"\"\"\n    return \"; \".join(f\"shot {i}, {int(e.duration)}, {e.prompt}\" for i, e in enumerate(multi_prompt, 1)) + \";\"\n\n\ndef _turbo_video_url(response: Kling3TurboQueryResponse) -> str:\n    \"\"\"Extract the result video URL from a /tasks response (data[].outputs[] where type == 'video').\"\"\"\n    task = response.data[0] if response.data else None\n    if task and task.outputs:\n        for output in task.outputs:\n            if output.type == \"video\" and output.url:\n                return output.url\n    raise RuntimeError(f\"Kling 3.0 Turbo task finished without a video output: {response.model_dump()}\")\n\n\nasync def execute_kling_turbo(\n    cls: type[IO.ComfyNode],\n    *,\n    prompt: str,\n    resolution: str,\n    aspect_ratio: str,\n    duration: int,\n    start_frame: torch.Tensor | None,\n) -> IO.NodeOutput:\n    \"\"\"Create + poll a Kling 3.0 Turbo task. Image-to-video when start_frame is given, else text-to-video.\"\"\"\n    if start_frame is not None:\n        validate_image_dimensions(start_frame, min_width=300, min_height=300)\n        validate_image_aspect_ratio(start_frame, (1, 2.5), (2.5, 1))\n        contents = [Kling3TurboContent(type=\"first_frame\", url=tensor_to_base64_string(start_frame))]\n        if prompt:\n            contents.insert(0, Kling3TurboContent(type=\"prompt\", text=prompt))","sourceCodeStart":2198,"sourceCodeEnd":2234,"githubUrl":"https://github.com/Comfy-Org/ComfyUI/blob/1c6d8d45b3693bfbb32385b410d813a7fd6be216/comfy_api_nodes/nodes_kling.py#L2198-L2234","documentation":"Raised when a Kling 3.0 Turbo task reaches a finished state but its /tasks result contains no output entry with type == 'video' and a non-empty url. The job technically completed but produced no downloadable video, which the node treats as a hard failure instead of returning garbage.","triggerScenarios":"poll_op on /proxy/kling/tasks?task_ids=<id> returns a Kling3TurboQueryResponse whose data[0].outputs is empty, missing, or has no {'type': 'video', 'url': non-empty} entry — e.g. the task failed server-side with status 'failed' but poll_op returned it, or outputs only contain metadata.","commonSituations":"Turbo generation failed on Kling's side (content policy, internal error) yet reported a terminal status; API response shape changed so outputs use a different type string; transient server bug returning an incomplete task record.","solutions":["Re-run the task once — transient Kling-side generation failures are the most common cause.","Inspect response.model_dump() in the error text to see the task status and outputs actually returned; a 'failed' status means the prompt/settings were rejected server-side.","Simplify the prompt (the 'shot n, m, words; ...' storyboard string must be well-formed) and confirm resolution/aspect_ratio/duration are valid Turbo settings.","If outputs consistently have a new shape (different type value), report a bug against comfy_api_nodes since the extractor only accepts type == 'video'."],"exampleFix":null,"handlingStrategy":"retry","validationCode":null,"typeGuard":"def turbo_has_video(resp: Kling3TurboQueryResponse) -> bool:\n    task = resp.data[0] if resp.data else None\n    return bool(task and task.outputs and any(o.type == \"video\" and o.url for o in task.outputs))","tryCatchPattern":"for attempt in range(2):\n    try:\n        return await execute_kling_turbo(...)\n    except RuntimeError as e:\n        if attempt == 0 and \"without a video output\" in str(e):\n            continue  # transient server-side generation failure, retry once\n        raise","preventionTips":["Keep Turbo prompts and settings conservative on first attempts.","Treat 'finished without video' as transient first, structural second.","Persist the task id from logs so you can query Kling's dashboard for the true failure reason."],"tags":["kling","api-nodes","turbo","polling","video"],"backgroundTag":null,"analyzedSha":"1c6d8d45b3693bfbb32385b410d813a7fd6be216","analyzedAt":"2026-08-14T19:37:18.893Z","schemaVersion":2},"datasetVersion":"2026-08-15T17:31:12.345Z"}