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

Code before:
                track_details.append(f'～{location}～')

            tracks.append(join_nonempty(*track_details, delim='\n'))

        return '\n\n'.join(tracks)

    def _format_description(self, response):
        act = traverse_obj(response, ('misc', 'actList', {self._format_actlist}))
        music = traverse_obj(response, ('misc', 'musicList', {self._format_musiclist}))
        desc = join_nonempty('epg80', 'epg200', delim='\n\n', from_dict=traverse_obj(response, 'detailedDescription'))

        return join_nonempty(desc, act, music, delim='\n\n')

    def _get_thumbnails(self, thumbs, name, preference=-1):
        thumbnails = []
        if thumbs is None or len(thumbs) == 0:
            return []
        for size, thumb in thumbs:
            if size == 'copyright' or not isinstance(thumb, dict):
                continue
            thumbnails.append({**thumb,
                               'preference': preference,
                               'id': join_nonempty(name, size),
                               })
            preference -= 1
        return thumbnails

    def _extract_extended_metadata(self, episode_id, aa_vinfo):
        service, _, area = traverse_obj(aa_vinfo, (2, {str}, {lambda x: (x or '').partition(',')}))
        dateid = aa_vinfo[3]

        detail_url = try_call(
            lambda: self._API_URL_TMPL.format(broadcastEventId=join_nonempty(service, area, dateid, delim='-')))
        if not detail_url:
            return {}

        response = self._download_json(
            detail_url, episode_id, 'Downloading extended metadata',
            'Failed to download extended metadata', fatal=False, expected_status=400)
        if not response:
            return {}

        if error := traverse_obj(response, ('error', {dict})):
            self.report_warning(
                'Failed to get extended metadata. API returned '
                f'Error {join_nonempty("statuscode", "message", from_dict=error, delim=": ")}')
            return {}

        station = traverse_obj(response, ('publishedOn', 'broadcastDisplayName'))

        about = response.get('about')

Review comment (suggestion):
- I'd rather that we not unpack a dict full of unknown input (`**thumb`), esp since this site seems to change its API frequently
- Let's do the traversal inside this method, which will make things both safer inside the method and simpler outside of the method
```suggestion
    def _get_thumbnails(self, data, keys, name=None, preference=-1):
        thumbnails = []
        for size, thumb in traverse_obj(data, (
            *variadic(keys, (str, bytes, dict, set)), {dict.items},
            lambda _, v: v[0] != 'copyright' and url_or_none(v[1]['url']),
        )):
            thumbnails.append({
                'url': thumb['url'],
                'width': int_or_none(thumb.get('width')),
                'height': int_or_none(thumb.get('height')),
                'preference': preference,
                'id': join_nonempty(name, size),
            })
            preference -= 1
        return thumbnails
```

Code after:
            thumbnails.append({
                'url': thumb['url'],
                'width': int_or_none(thumb.get('width')),
                'height': int_or_none(thumb.get('height')),
                'preference': preference,
                'id': join_nonempty(name, size),
            })
            preference -= 1
        return thumbnails

    def _extract_extended_metadata(self, episode_id, aa_vinfo):
        service, _, area = traverse_obj(aa_vinfo, (2, {str}, {lambda x: (x or '').partition(',')}))
        date_id = aa_vinfo[3]

        detail_url = try_call(
            lambda: self._API_URL_TMPL.format(broadcastEventId=join_nonempty(service, area, date_id)))
        if not detail_url:
            return {}

        response = self._download_json(
            detail_url, episode_id, 'Downloading extended metadata',
            'Failed to download extended metadata', fatal=False, expected_status=400)
        if not response:
            return {}

        if error := traverse_obj(response, ('error', {dict})):
            self.report_warning(
                'Failed to get extended metadata. API returned '
                f'Error {join_nonempty("statuscode", "message", from_dict=error, delim=": ")}')
            return {}

        station = traverse_obj(response, ('publishedOn', 'broadcastDisplayName', {str}))

        thumbnails = []
        thumbnails.extend(self._get_thumbnails(response, ('about', 'eyecatch')))
        for num, dct in enumerate(traverse_obj(response, ('about', 'eyecatchList', ...))):
            thumbnails.extend(self._get_thumbnails(dct, None, join_nonempty('list', num), -2))
        thumbnails.extend(
            self._get_thumbnails(response, ('about', 'partOfSeries', 'eyecatch'), 'series', -3))

        return filter_dict({
            'description': self._format_description(response),
            'cast': traverse_obj(response, ('misc', 'actList', ..., 'name', {str})),
            'thumbnails': thumbnails,
            **traverse_obj(response, {
                'title': ('name', {str}),
                'timestamp': ('endDate', {unified_timestamp}),
                'release_timestamp': ('startDate', {unified_timestamp}),
                'duration': ('duration', {parse_duration}),
            }),
            **traverse_obj(response, ('identifierGroup', {