T09 · Insecure Skill Coding Practices
- Location
scripts/tensorslab_video.py:75- Finding
Unrestricted Download of Server-Supplied URLs
- Content
View full analysis
Vulnerability Details
File Location:
scripts/tensorslab_video.py:75-98, 322-335
Vulnerability Type: Unvalidated remote URL retrieval
Risk Level: MediumVulnerable Code
python def download_video(url: str, output_path: Path) -> bool: """Download a video from URL to local path.""" try: response = _SESSION.get(url, timeout=300, stream=True) response.raise_for_status() total_size = int(response.headers.get('content-length', 0)) with open(output_path, 'wb') as f: if total_size > 0: downloaded = 0 for chunk in response.iter_content(chunk_size=8192): if chunk: f.write(chunk) downloaded += len(chunk) percent = (downloaded / total_size) * 100 logger.info(f"\r📥 Downloading: {percent:.1f}%") else: f.write(response.content) logger.info(f"\r✅ Download complete: {output_path}") return True except Exception as e: logger.warning(f"\r⚠️ Failed to download video from {url}: {e}") return FalseThe download function is reached using URLs supplied by the task-status API:
python urls = task_data.get("url", []) if not urls: logger.warning("⚠️ No videos returned") return downloaded_files for i, url in enumerate(urls): url_path = urlparse(url).path ext = Path(url_path).suffix if not ext or len(ext) > 5: ext = ".mp4" filename = f"{task_id}_{i}{ext}" output_path = output_dir / filename logger.info(f"📥 Downloading video {i+1}/{len(urls)}: {output_path}") if download_video(url, output_path): downloaded_files.append(str(output_path))Technical Analysis
URLs returned by the remote task-status endpoint are passed direct ...[truncated 2322 chars]
- Remediation
View remediation
Remediation Suggestions
- Permit only
httpsURLs. - Maintain an explicit allowlist of documented TensorsLab media/CDN hostnames.
- Resolve the hostname before connecting and reject loopback, private, link-local, multicast, unspecified, and reserved IPv4 and IPv6 addresses.
- Disable redirects or validate the scheme, hostname, and resolved address of every redirect destination.
- Verify that the response has an expected video content type before writing it.
- Enforce a maximum response size both from
Content-Lengthand while streaming, aborting when the cumulative byte count exceeds the limit. - Download to a temporary file and atomically rename it only after all validation succeeds; remove partial files on failure.
- Use separate connection and read timeouts and cap the number of redirects.
- Permit only
