calesthio/OpenMontage · error · ValueError
Kling TTS response item contained no downloadable URL: {item
Error message
Kling TTS response item contained no downloadable URL: {item} What it means
Raised as ValueError by the static _output_url helper when a single audios entry has none of the known URL keys: url, audio_url, resource_url, or resource.url. It is a per-item shape check with the entire item embedded in the message, so the offending object is visible in the error.
Source
Thrown at tools/audio/kling_tts.py:302
base_path = Path(inputs.get("output_path", "kling_tts.mp3"))
paths: list[Path] = []
for index, item in enumerate(outputs):
url = self._output_url(item)
suffix = extension_from_url(url, ".mp3")
output_path = numbered_output_path(output_path_with_suffix(base_path, suffix), index, suffix)
client.download(url, output_path)
paths.append(output_path)
return paths
@staticmethod
def _output_url(item: dict[str, Any]) -> str:
url = item.get("url") or item.get("audio_url") or item.get("resource_url")
if url:
return str(url)
resource = item.get("resource") or {}
if isinstance(resource, dict) and resource.get("url"):
return str(resource["url"])
raise ValueError(f"Kling TTS response item contained no downloadable URL: {item}")
@staticmethod
def _copy_common_task_fields(inputs: dict[str, Any], payload: dict[str, Any]) -> None:
callback_url = validate_callback_url(inputs.get("callback_url"))
if callback_url:
payload["callback_url"] = callback_url
if inputs.get("external_task_id"):
payload["external_task_id"] = inputs["external_task_id"]
@staticmethod
def _callback_result_data(inputs: dict[str, Any], task_id: str) -> dict[str, Any]:
callback_url = inputs.get("callback_url")
if not callback_url:
return {}
return {
"callback_url": str(callback_url),
"callback_requested": True,
"polling_used": True,View on GitHub (pinned to 95e1c3d0ab)
Solutions
- Inspect the embedded item in the error message to find the new key name
- Extend _output_url's key chain (url → audio_url → resource_url → resource.url) with the new key
- If the item holds an id/path, add a follow-up fetch to resolve it to a URL
Example fix
// before
url = item.get("url") or item.get("audio_url") or item.get("resource_url")
// after
url = (
item.get("url")
or item.get("audio_url")
or item.get("resource_url")
or item.get("file_url") # new upstream key
) Defensive patterns
Strategy: validation
Validate before calling
def item_has_url(item: dict) -> bool:
return bool(
item.get("url") or item.get("audio_url") or item.get("resource_url")
or (isinstance(item.get("resource"), dict) and item["resource"].get("url"))
) Type guard
def is_downloadable_item(item: Any) -> bool:
if not isinstance(item, dict):
return False
resource = item.get("resource")
return bool(
item.get("url") or item.get("audio_url") or item.get("resource_url")
or (isinstance(resource, dict) and resource.get("url"))
) Try / catch
try:
paths = kling_tts_tool._download_audios(client, outputs, inputs)
except ValueError as e:
if "no downloadable URL" in str(e):
logger.error("kling audio item schema changed: %s", e)
raise Prevention
- The full offending item is embedded in the message — read it before changing code
- Extend the URL-key chain when upstream adds fields, keeping old keys for compat
- Keep test fixtures sourced from captured real responses
When it happens
Trigger: Kling changes the per-audio object schema (new key like 'file_url'); item contains only a task-relative path or an id requiring a second fetch; gateway strips URL fields.
Common situations: API version drift adding/renameing URL fields; items that reference a resource endpoint instead of a direct URL; test fixtures built from outdated docs.
Related errors
- Kling TTS create response missing data.task_id: {data}
- Kling TTS result path data.task_result.audios is not a list
- Kling TTS response contained no audios
- Kling Classic create response missing data.task_id: {data}
- Doubao submit succeeded but did not return data.task_id
AI-assisted analysis of calesthio/OpenMontage@95e1c3d0ab (2026-08-15).
Data as JSON: /api/errors/7504cab68acc18db.
Report an issue: GitHub.