mirror of
				https://gitlab.com/ytdl-org/youtube-dl.git
				synced 2025-11-04 10:27:07 -05:00 
			
		
		
		
	[crunchyroll] extract old rtmp formats
This commit is contained in:
		@@ -38,6 +38,16 @@ class CrunchyrollBaseIE(InfoExtractor):
 | 
			
		||||
    _LOGIN_FORM = 'login_form'
 | 
			
		||||
    _NETRC_MACHINE = 'crunchyroll'
 | 
			
		||||
 | 
			
		||||
    def _call_rpc_api(self, method, video_id, note=None, data=None):
 | 
			
		||||
        data = data or {}
 | 
			
		||||
        data['req'] = 'RpcApi' + method
 | 
			
		||||
        data = compat_urllib_parse_urlencode(data).encode('utf-8')
 | 
			
		||||
        return self._download_xml(
 | 
			
		||||
            'http://www.crunchyroll.com/xml/',
 | 
			
		||||
            video_id, note, fatal=False, data=data, headers={
 | 
			
		||||
                'Content-Type': 'application/x-www-form-urlencoded',
 | 
			
		||||
            })
 | 
			
		||||
 | 
			
		||||
    def _login(self):
 | 
			
		||||
        (username, password) = self._get_login_info()
 | 
			
		||||
        if username is None:
 | 
			
		||||
@@ -377,15 +387,19 @@ Format: Layer, Start, End, Style, Name, MarginL, MarginR, MarginV, Effect, Text
 | 
			
		||||
    def _get_subtitles(self, video_id, webpage):
 | 
			
		||||
        subtitles = {}
 | 
			
		||||
        for sub_id, sub_name in re.findall(r'\bssid=([0-9]+)"[^>]+?\btitle="([^"]+)', webpage):
 | 
			
		||||
            sub_page = self._download_webpage(
 | 
			
		||||
                'http://www.crunchyroll.com/xml/?req=RpcApiSubtitle_GetXml&subtitle_script_id=' + sub_id,
 | 
			
		||||
                video_id, note='Downloading subtitles for ' + sub_name)
 | 
			
		||||
            id = self._search_regex(r'id=\'([0-9]+)', sub_page, 'subtitle_id', fatal=False)
 | 
			
		||||
            iv = self._search_regex(r'<iv>([^<]+)', sub_page, 'subtitle_iv', fatal=False)
 | 
			
		||||
            data = self._search_regex(r'<data>([^<]+)', sub_page, 'subtitle_data', fatal=False)
 | 
			
		||||
            if not id or not iv or not data:
 | 
			
		||||
            sub_doc = self._call_rpc_api(
 | 
			
		||||
                'Subtitle_GetXml', video_id,
 | 
			
		||||
                'Downloading subtitles for ' + sub_name, data={
 | 
			
		||||
                    'subtitle_script_id': sub_id,
 | 
			
		||||
                })
 | 
			
		||||
            if not sub_doc:
 | 
			
		||||
                continue
 | 
			
		||||
            subtitle = self._decrypt_subtitles(data, iv, id).decode('utf-8')
 | 
			
		||||
            sid = sub_doc.get('id')
 | 
			
		||||
            iv = xpath_text(sub_doc, 'iv', 'subtitle iv')
 | 
			
		||||
            data = xpath_text(sub_doc, 'data', 'subtitle data')
 | 
			
		||||
            if not sid or not iv or not data:
 | 
			
		||||
                continue
 | 
			
		||||
            subtitle = self._decrypt_subtitles(data, iv, sid).decode('utf-8')
 | 
			
		||||
            lang_code = self._search_regex(r'lang_code=["\']([^"\']+)', subtitle, 'subtitle_lang_code', fatal=False)
 | 
			
		||||
            if not lang_code:
 | 
			
		||||
                continue
 | 
			
		||||
@@ -456,65 +470,79 @@ Format: Layer, Start, End, Style, Name, MarginL, MarginR, MarginV, Effect, Text
 | 
			
		||||
        for fmt in available_fmts:
 | 
			
		||||
            stream_quality, stream_format = self._FORMAT_IDS[fmt]
 | 
			
		||||
            video_format = fmt + 'p'
 | 
			
		||||
            streamdata_req = sanitized_Request(
 | 
			
		||||
                'http://www.crunchyroll.com/xml/?req=RpcApiVideoPlayer_GetStandardConfig&media_id=%s&video_format=%s&video_quality=%s'
 | 
			
		||||
                % (video_id, stream_format, stream_quality),
 | 
			
		||||
                compat_urllib_parse_urlencode({'current_page': url}).encode('utf-8'))
 | 
			
		||||
            streamdata_req.add_header('Content-Type', 'application/x-www-form-urlencoded')
 | 
			
		||||
            streamdata = self._download_xml(
 | 
			
		||||
                streamdata_req, video_id,
 | 
			
		||||
                note='Downloading media info for %s' % video_format)
 | 
			
		||||
            stream_info = streamdata.find('./{default}preload/stream_info')
 | 
			
		||||
            video_encode_id = xpath_text(stream_info, './video_encode_id')
 | 
			
		||||
            if video_encode_id in video_encode_ids:
 | 
			
		||||
                continue
 | 
			
		||||
            video_encode_ids.append(video_encode_id)
 | 
			
		||||
            stream_infos = []
 | 
			
		||||
            streamdata = self._call_rpc_api(
 | 
			
		||||
                'VideoPlayer_GetStandardConfig', video_id,
 | 
			
		||||
                'Downloading media info for %s' % video_format, data={
 | 
			
		||||
                    'media_id': video_id,
 | 
			
		||||
                    'video_format': stream_format,
 | 
			
		||||
                    'video_quality': stream_quality,
 | 
			
		||||
                    'current_page': url,
 | 
			
		||||
                })
 | 
			
		||||
            if streamdata:
 | 
			
		||||
                stream_info = streamdata.find('./{default}preload/stream_info')
 | 
			
		||||
                if stream_info:
 | 
			
		||||
                    stream_infos.append(stream_info)
 | 
			
		||||
            stream_info = self._call_rpc_api(
 | 
			
		||||
                'VideoEncode_GetStreamInfo', video_id,
 | 
			
		||||
                'Downloading stream info for %s' % video_format, data={
 | 
			
		||||
                    'media_id': video_id,
 | 
			
		||||
                    'video_format': stream_format,
 | 
			
		||||
                    'video_encode_quality': stream_quality,
 | 
			
		||||
                })
 | 
			
		||||
            if stream_info:
 | 
			
		||||
                stream_infos.append(stream_info)
 | 
			
		||||
            for stream_info in stream_infos:
 | 
			
		||||
                video_encode_id = xpath_text(stream_info, './video_encode_id')
 | 
			
		||||
                if video_encode_id in video_encode_ids:
 | 
			
		||||
                    continue
 | 
			
		||||
                video_encode_ids.append(video_encode_id)
 | 
			
		||||
 | 
			
		||||
            video_file = xpath_text(stream_info, './file')
 | 
			
		||||
            if not video_file:
 | 
			
		||||
                continue
 | 
			
		||||
            if video_file.startswith('http'):
 | 
			
		||||
                formats.extend(self._extract_m3u8_formats(
 | 
			
		||||
                    video_file, video_id, 'mp4', entry_protocol='m3u8_native',
 | 
			
		||||
                    m3u8_id='hls', fatal=False))
 | 
			
		||||
                continue
 | 
			
		||||
 | 
			
		||||
            video_url = xpath_text(stream_info, './host')
 | 
			
		||||
            if not video_url:
 | 
			
		||||
                continue
 | 
			
		||||
            metadata = stream_info.find('./metadata')
 | 
			
		||||
            format_info = {
 | 
			
		||||
                'format': video_format,
 | 
			
		||||
                'format_id': video_format,
 | 
			
		||||
                'height': int_or_none(xpath_text(metadata, './height')),
 | 
			
		||||
                'width': int_or_none(xpath_text(metadata, './width')),
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            if '.fplive.net/' in video_url:
 | 
			
		||||
                video_url = re.sub(r'^rtmpe?://', 'http://', video_url.strip())
 | 
			
		||||
                parsed_video_url = compat_urlparse.urlparse(video_url)
 | 
			
		||||
                direct_video_url = compat_urlparse.urlunparse(parsed_video_url._replace(
 | 
			
		||||
                    netloc='v.lvlt.crcdn.net',
 | 
			
		||||
                    path='%s/%s' % (remove_end(parsed_video_url.path, '/'), video_file.split(':')[-1])))
 | 
			
		||||
                if self._is_valid_url(direct_video_url, video_id, video_format):
 | 
			
		||||
                    format_info.update({
 | 
			
		||||
                        'url': direct_video_url,
 | 
			
		||||
                    })
 | 
			
		||||
                    formats.append(format_info)
 | 
			
		||||
                video_file = xpath_text(stream_info, './file')
 | 
			
		||||
                if not video_file:
 | 
			
		||||
                    continue
 | 
			
		||||
                if video_file.startswith('http'):
 | 
			
		||||
                    formats.extend(self._extract_m3u8_formats(
 | 
			
		||||
                        video_file, video_id, 'mp4', entry_protocol='m3u8_native',
 | 
			
		||||
                        m3u8_id='hls', fatal=False))
 | 
			
		||||
                    continue
 | 
			
		||||
 | 
			
		||||
            format_info.update({
 | 
			
		||||
                'url': video_url,
 | 
			
		||||
                'play_path': video_file,
 | 
			
		||||
                'ext': 'flv',
 | 
			
		||||
            })
 | 
			
		||||
            formats.append(format_info)
 | 
			
		||||
        self._sort_formats(formats)
 | 
			
		||||
                video_url = xpath_text(stream_info, './host')
 | 
			
		||||
                if not video_url:
 | 
			
		||||
                    continue
 | 
			
		||||
                metadata = stream_info.find('./metadata')
 | 
			
		||||
                format_info = {
 | 
			
		||||
                    'format': video_format,
 | 
			
		||||
                    'height': int_or_none(xpath_text(metadata, './height')),
 | 
			
		||||
                    'width': int_or_none(xpath_text(metadata, './width')),
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
        metadata = self._download_xml(
 | 
			
		||||
            'http://www.crunchyroll.com/xml', video_id,
 | 
			
		||||
            note='Downloading media info', query={
 | 
			
		||||
                'req': 'RpcApiVideoPlayer_GetMediaMetadata',
 | 
			
		||||
                if '.fplive.net/' in video_url:
 | 
			
		||||
                    video_url = re.sub(r'^rtmpe?://', 'http://', video_url.strip())
 | 
			
		||||
                    parsed_video_url = compat_urlparse.urlparse(video_url)
 | 
			
		||||
                    direct_video_url = compat_urlparse.urlunparse(parsed_video_url._replace(
 | 
			
		||||
                        netloc='v.lvlt.crcdn.net',
 | 
			
		||||
                        path='%s/%s' % (remove_end(parsed_video_url.path, '/'), video_file.split(':')[-1])))
 | 
			
		||||
                    if self._is_valid_url(direct_video_url, video_id, video_format):
 | 
			
		||||
                        format_info.update({
 | 
			
		||||
                            'format_id': 'http-' + video_format,
 | 
			
		||||
                            'url': direct_video_url,
 | 
			
		||||
                        })
 | 
			
		||||
                        formats.append(format_info)
 | 
			
		||||
                        continue
 | 
			
		||||
 | 
			
		||||
                format_info.update({
 | 
			
		||||
                    'format_id': 'rtmp-' + video_format,
 | 
			
		||||
                    'url': video_url,
 | 
			
		||||
                    'play_path': video_file,
 | 
			
		||||
                    'ext': 'flv',
 | 
			
		||||
                })
 | 
			
		||||
                formats.append(format_info)
 | 
			
		||||
        self._sort_formats(formats, ('height', 'width', 'tbr', 'fps'))
 | 
			
		||||
 | 
			
		||||
        metadata = self._call_rpc_api(
 | 
			
		||||
            'VideoPlayer_GetMediaMetadata', video_id,
 | 
			
		||||
            note='Downloading media info', data={
 | 
			
		||||
                'media_id': video_id,
 | 
			
		||||
            })
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user