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

Code before:
            'ext': 'm4a',
            'view_count': int,
            'thumbnail': r're:^https?://.*\.jpg',
            'like_count': int,
        },
        'params': {
            'skip_download': True,
        },
    }]

    def _real_extract(self, url):
        url_type, live_radio_id = self._match_valid_url(url).group('type', 'id')
        info = self._call_api(url_type, {'id': live_radio_id})
        manifest_url = info.get('streaming')
        if not manifest_url:
            raise ExtractorError('This radio is offline.', expected=True)
        fmts, subtitles = self._extract_m3u8_formats_and_subtitles(manifest_url, live_radio_id, fatal=False)
        return {
            'id': live_radio_id,
            'title': traverse_obj(info, 'title'),
            'thumbnail': traverse_obj(info, 'thumbnail', 'thumbnailM', 'thumbnailV', 'thumbnailH'),
            'formats': fmts,
            'view_count': traverse_obj(info, 'activeUsers'),
            'like_count': traverse_obj(info, 'totalReaction'),
            'description': traverse_obj(info, 'description'),
            'subtitles': subtitles,
        }


class ZingMp3PostCastEpisodeIE(ZingMp3BaseIE):
    IE_NAME = 'zingmp3:PostcastEpisode'
    _VALID_URL = ZingMp3BaseIE._VALID_URL_TMPL % 'pgr|cgr'
    _TESTS = [{
        'url': 'https://zingmp3.vn/pgr/How2Money-x-Doctor-Housing/6BUUFAEO.html',
        'info_dict': {
            'id': '6BUUFAEO',
            'title': 'How2Money x Doctor Housing',
            'description': 'md5:3c1eb04aaa28fee0805629d9b766d05c'
        },
        'playlist_mincount': 20,
    }, {
        'url': 'https://zingmp3.vn/cgr/Am-nhac/IWZ980AO.html',
        'info_dict': {
            'id': 'IWZ980AO',
            'title': 'Âm nhạc'
        },
        'playlist_mincount': 20,
    }]

    def _fetch_page(self, eps_id, url_type, page):
        return self._call_api(url_type, {

Review comment (suggestion):
Need to set `'is_live': True` since the native m3u8 downloader currently does not support livestreams and instead ffmpeg needs to be used.
The `traverse_obj` calls can also be combined
```suggestion
            'id': live_radio_id,
            'is_live': True,
            'formats': fmts,
            'subtitles': subtitles,
            **traverse_obj(info, {
                'title': 'title',
                'thumbnail': (None, ('thumbnail', 'thumbnailM', 'thumbnailV', 'thumbnailH'), {url_or_none}),
                'view_count': ('activeUsers', {int_or_none}),
                'like_count': ('totalReaction', {int_or_none}),
                'description': 'description',
            }, get_all=False),
```

Code after:
            'view_count': int,
            'thumbnail': r're:^https?://.*\.jpg',
            'like_count': int,
            'live_status': 'is_live',
        },
        'params': {
            'skip_download': True,
        },
    }]

    def _real_extract(self, url):
        url_type, live_radio_id = self._match_valid_url(url).group('type', 'id')
        info = self._call_api(url_type, {'id': live_radio_id})
        manifest_url = info.get('streaming')
        if not manifest_url:
            raise ExtractorError('This radio is offline.', expected=True)
        fmts, subtitles = self._extract_m3u8_formats_and_subtitles(manifest_url, live_radio_id, fatal=False)
        return {
            'id': live_radio_id,
            'is_live': True,
            'formats': fmts,
            'subtitles': subtitles,
            **traverse_obj(info, {
                'title': 'title',
                'thumbnail': (('thumbnail', 'thumbnailM', 'thumbnailV', 'thumbnailH'), {url_or_none}),
                'view_count': ('activeUsers', {int_or_none}),
                'like_count': ('totalReaction', {int_or_none}),
                'description': 'description',
            }, get_all=False),
        }


class ZingMp3PodcastEpisodeIE(ZingMp3BaseIE):
    IE_NAME = 'zingmp3:podcast-episode'
    _VALID_URL = ZingMp3BaseIE._VALID_URL_TMPL % 'pgr|cgr'
    _TESTS = [{
        'url': 'https://zingmp3.vn/pgr/Nhac-Moi-Moi-Ngay/68Z9W66B.html',
        'info_dict': {
            'id': '68Z9W66B',
            'title': 'Nhạc Mới Mỗi Ngày',
            'description': 'md5:2875dfa951f8e5356742f1610cf20691'
        },
        'playlist_mincount': 20,
    }, {
        'url': 'https://zingmp3.vn/cgr/Am-nhac/IWZ980AO.html',
        'info_dict': {
            'id': 'IWZ980AO',
            'title': 'Âm nhạc'
        },
        'playlist_mincount': 2,
    }]