Repository: yt-dlp/yt-dlp
File: yt_dlp/extractor/common.py (Python)

Code before:
            re.findall(sep_re % (duration_re, r'.+?'), description or ''),
            start_function=lambda x: parse_duration(x[0]), title_function=lambda x: x[1],
            duration=duration, strict=False) or self._extract_chapters_helper(
            re.findall(sep_re % (r'.+?', duration_re), description or ''),
            start_function=lambda x: parse_duration(x[1]), title_function=lambda x: x[0],
            duration=duration, strict=False)

    def _extract_heatmap_helper(self, heatmap_list, start_function, end_function, value_function, strict=True):
        heatmap_list = [{
            'start_time': start_function(point),
            'end_time': end_function(point),
            'value': value_function(point),
        } for point in heatmap_list or []]
        if strict:
            warn = self.report_warning
        else:
            warn = self.write_debug
            heatmap_list.sort(key=lambda p: p['start_time'] or 0)

        heatmap = [{'start_time': 0}]
        for idx, point in enumerate(heatmap_list):
            if None in point.values():
                warn(f'Incomplete heatmap point {idx}')
            elif heatmap[-1]['start_time'] <= point['start_time']:
                heatmap.append(point)
        return heatmap[1:]

    @staticmethod
    def _availability(is_private=None, needs_premium=None, needs_subscription=None, needs_auth=None, is_unlisted=None):
        all_known = all(map(
            lambda x: x is not None,
            (is_private, needs_premium, needs_subscription, needs_auth, is_unlisted)))
        return (
            'private' if is_private
            else 'premium_only' if needs_premium
            else 'subscriber_only' if needs_subscription
            else 'needs_auth' if needs_auth
            else 'unlisted' if is_unlisted
            else 'public' if all_known
            else None)

    def _configuration_arg(self, key, default=NO_DEFAULT, *, ie_key=None, casesense=False):
        '''
        @returns            A list of values for the extractor argument given by "key"
                            or "default" if no such key is present
        @param default      The default value to return when the key is not present (default: [])
        @param casesense    When false, the values are converted to lower case
        '''
        ie_key = ie_key if isinstance(ie_key, str) else (ie_key or self).ie_key()
        val = traverse_obj(self._downloader.params, ('extractor_args', ie_key.lower(), key))
        if val is None:

Review comment (suggestion):
I think it makes sense to have it print out the faulty point instead of the index:
```suggestion
        heatmap = []
        for point in heatmap_list:
            if None in point.values():
                warn(f'Incomplete heatmap point: {point}')
                continue
            heatmap.append(point)
        return heatmap
```

Code after:
    def _extract_chapters_from_description(self, description, duration):
        duration_re = r'(?:\d+:)?\d{1,2}:\d{2}'
        sep_re = r'(?m)^\s*(%s)\b\W*\s(%s)\s*$'
        return self._extract_chapters_helper(
            re.findall(sep_re % (duration_re, r'.+?'), description or ''),
            start_function=lambda x: parse_duration(x[0]), title_function=lambda x: x[1],
            duration=duration, strict=False) or self._extract_chapters_helper(
            re.findall(sep_re % (r'.+?', duration_re), description or ''),
            start_function=lambda x: parse_duration(x[1]), title_function=lambda x: x[0],
            duration=duration, strict=False)

    @staticmethod
    def _availability(is_private=None, needs_premium=None, needs_subscription=None, needs_auth=None, is_unlisted=None):
        all_known = all(map(
            lambda x: x is not None,
            (is_private, needs_premium, needs_subscription, needs_auth, is_unlisted)))
        return (
            'private' if is_private
            else 'premium_only' if needs_premium
            else 'subscriber_only' if needs_subscription
            else 'needs_auth' if needs_auth
            else 'unlisted' if is_unlisted
            else 'public' if all_known
            else None)

    def _configuration_arg(self, key, default=NO_DEFAULT, *, ie_key=None, casesense=False):
        '''
        @returns            A list of values for the extractor argument given by "key"
                            or "default" if no such key is present
        @param default      The default value to return when the key is not present (default: [])
        @param casesense    When false, the values are converted to lower case
        '''
        ie_key = ie_key if isinstance(ie_key, str) else (ie_key or self).ie_key()
        val = traverse_obj(self._downloader.params, ('extractor_args', ie_key.lower(), key))
        if val is None:
            return [] if default is NO_DEFAULT else default
        return list(val) if casesense else [x.lower() for x in val]

    def _yes_playlist(self, playlist_id, video_id, smuggled_data=None, *, playlist_label='playlist', video_label='video'):
        if not playlist_id or not video_id:
            return not video_id

        no_playlist = (smuggled_data or {}).get('force_noplaylist')
        if no_playlist is not None:
            return not no_playlist

        video_id = '' if video_id is True else f' {video_id}'
        playlist_id = '' if playlist_id is True else f' {playlist_id}'
        if self.get_param('noplaylist'):
            self.to_screen(f'Downloading just the {video_label}{video_id} because of --no-playlist')
            return False