yt-dlp/yt-dlp · error · DownloadError
Unable to download video subtitles for {sub_lang!r}: {err}
Error message
Unable to download video subtitles for {sub_lang!r}: {err} What it means
Raised by YoutubeDL._download_subtitle when the actual subtitle file download (self.dl on the subtitle URL) fails with DownloadError, ExtractorError, OSError, ValueError, or any network exception. The message embeds the language code (e.g. 'en') and the underlying error text. Behavior depends on 'ignoreerrors': when False, report_error() prints it and a DownloadError is raised (aborting the video); when 'only_download', DownloadError is raised for the caller to catch; when True, it degrades to a warning and processing continues.
Source
Thrown at yt_dlp/YoutubeDL.py:4501
sub_info['filepath'] = sub_filename
ret.append((sub_filename, sub_filename_final))
continue
except OSError:
self.report_error(f'Cannot write video subtitles file {sub_filename}')
return None
try:
sub_copy = sub_info.copy()
sub_copy.setdefault('http_headers', info_dict.get('http_headers'))
self.dl(sub_filename, sub_copy, subtitle=True)
sub_info['filepath'] = sub_filename
ret.append((sub_filename, sub_filename_final))
except (DownloadError, ExtractorError, OSError, ValueError, *network_exceptions) as err:
msg = f'Unable to download video subtitles for {sub_lang!r}: {err}'
if self.params.get('ignoreerrors') is not True: # False or 'only_download'
if not self.params.get('ignoreerrors'):
self.report_error(msg)
raise DownloadError(msg)
self.report_warning(msg)
return ret
def _write_thumbnails(self, label, info_dict, filename, thumb_filename_base=None):
""" Write thumbnails to file and return list of (thumb_filename, final_thumb_filename); or None if error """
write_all = self.params.get('write_all_thumbnails', False)
thumbnails, ret = [], []
if write_all or self.params.get('writethumbnail', False):
thumbnails = info_dict.get('thumbnails') or []
if not thumbnails:
self.to_screen(f'[info] There are no {label} thumbnails to download')
return ret
multiple = write_all and len(thumbnails) > 1
if thumb_filename_base is None:
thumb_filename_base = filename
if thumbnails and not thumb_filename_base:
self.write_debug(f'Skipping writing {label} thumbnail')View on GitHub (pinned to 81ecd58b13)
Solutions
- Read the wrapped {err} text — it names the real cause (HTTP 404, timeout, etc.) and that is what must be fixed.
- If missing subs are acceptable, set 'ignoreerrors': True (CLI: --ignore-errors) so the failure becomes a warning and the batch continues.
- Verify the language actually exists in info_dict['subtitles'] / info_dict['automatic_captions'] before enabling subtitle download for that code.
- For authentication-dependent subtitles, pass cookies via 'cookiefile' so the subtitle request is authorized.
- Retry later if the subtitle URL was extracted long before download (URL expiry).
Example fix
# before
ydl_opts = {'writesubtitles': True, 'subtitleslangs': ['en']}
# after: tolerate missing subs so the rest of the batch survives
ydl_opts = {'writesubtitles': True, 'subtitleslangs': ['en'], 'ignoreerrors': True} Defensive patterns
Strategy: try-catch
Try / catch
from yt_dlp import YoutubeDL
from yt_dlp.utils import DownloadError
with YoutubeDL(opts) as ydl:
try:
ydl.download([url])
except DownloadError as err:
if 'Unable to download video subtitles' in str(err):
log.warning('subtitles unavailable for %s: %s', url, err) # continue batch
else:
raise Prevention
- Before download, check info = ydl.extract_info(url, download=False) and confirm the language exists in info['subtitles'] or info['automatic_captions'].
- For batch jobs set 'ignoreerrors': True so subtitle failures downgrade to warnings.
- Pass 'cookiefile' when subtitles require the same auth as the video.
- Treat subtitle URLs as short-lived: avoid long gaps between extract_info and download.
When it happens
Trigger: Running ydl.download()/ydl.extract_info() with writesubtitles/writeautomaticsub and subtitleslangs set, where the subtitle URL returns 404/403, the extractor published a stale subtitle URL, a connection error occurs, or the sub_info dict is malformed (ValueError). Also hit when a subtitle format requires headers/cookies not forwarded from info_dict['http_headers'].
Common situations: Batch downloads with --write-subs where one video's subtitle track is missing or geo-blocked; YouTube auto-caption URLs expiring before download; subtitles listed by the extractor but later removed; corporate proxies causing network_exceptions.
Related errors
- {e}. Retrying{format_field(suffix, None, " %s")} ({count}/{r
- Impersonate target "{impersonate_target}" is not available.
- Invalid js_runtimes format, expected a dict of {runtime: {co
- Wrong regex for allowed_extractors: {e.pattern}
- Unsafe conversion(s) in exec command: {outtmpl!r} Conversion
AI-assisted analysis of yt-dlp/yt-dlp@81ecd58b13 (2026-08-22).
Data as JSON: /api/errors/2eec7c6ba45f3c3e.
Report an issue: GitHub.