ytdl-org/youtube-dl · error · ExtractorError

No stream data/URL

Error message

No stream data/URL

What it means

Raised by the GB News extractor after fetching <api_hostname>/api/<type>/stream/<uvid> when response.stream is missing or not a valid URL (traverse_obj with url_or_none filter). The stream request uses fatal=False, so HTTP failures also arrive here with stream_data set to None.

Source

Thrown at youtube_dl/extractor/gbnews.py:114

        uvid = video_data['data-uvid']
        dtype = video_data.get('data-type')
        stream_data = self._download_json(
            '%s/api/%s/stream/%s' % (meta_url, 'show' if dtype == 'vod' else dtype, uvid),
            uvid,
            query={
                'key': video_data.get('data-key'),
                'platform': self._PLATFORM,
            },
            headers={
                'Token': video_data.get('data-token'),
                'Token-Expiry': video_data.get('data-expiry'),
                'Uvid': uvid,
            }, fatal=False)

        stream_url = traverse_obj(stream_data, (
            'response', 'stream', T(url_or_none)))
        if not stream_url:
            raise ExtractorError('No stream data/URL')

        # now known to be a dict
        stream_data = stream_data['response']
        drm = stream_data.get('drm')
        if drm:
            self.report_drm(uvid)

        formats = self._extract_m3u8_formats(
            stream_url, uvid, ext='mp4', entry_protocol='m3u8_native',
            fatal=False)
        # exception if no formats
        self._sort_formats(formats)

        return {
            'id': uvid,
            'display_id': display_id,
            'title': (traverse_obj(stream_data, ('title', T(txt_or_none)))
                      or self._og_search_title(webpage, default=None)

View on GitHub (pinned to 956b8c5855)

Solutions

  1. Re-download the page fresh (clear cache) so data-token/data-expiry are current and retry
  2. Run with -v to confirm the stream API request/response behind the swallowed failure
  3. Check geo/VPN: GB News streams are typically UK-only
  4. Update youtube-dl/yt-dlp; if still failing, extract the stream URL manually from devtools
Defensive patterns

Strategy: try-catch

Validate before calling

import requests
r = requests.get(f'{api_hostname}/api/{dtype}/stream/{uvid}', headers=hdrs, params={'platform': 'gbnews'})
stream = r.json().get('response', {}).get('stream')
if not isinstance(stream, str) or not stream.startswith('http'):
    print('Stream endpoint returned no playable URL (token/geo/DRM?)')

Type guard

from youtube_dl.utils import url_or_none
def stream_url_ok(stream_data):
    return url_or_none(stream_data and stream_data.get('response', {}).get('stream')) is not None

Try / catch

try:
    info = ydl.extract_info(url)
except DownloadError as e:
    if 'No stream data/URL' in str(e):
        refetch_page_and_retry(url)  # tokens in the page may be stale
    else:
        raise

Prevention

When it happens

Trigger: The stream API rejects the Token/Token-Expiry/Uvid headers (expired token from the page), returns DRM-only or geo-blocked content with no stream URL, or the request failed silently due to fatal=False.

Common situations: Stale page HTML with expired tokens (page cached long before extraction), geo-restriction to the UK, DRM-protected streams, or an API response-shape change by Simplestream.

Related errors


AI-assisted analysis of ytdl-org/youtube-dl@956b8c5855 (2026-08-14). Data as JSON: /api/errors/a2e38360a9cbd7c5. Report an issue: GitHub.