diff options
| -rw-r--r-- | youtube_dl/extractor/youtube.py | 62 | 
1 files changed, 41 insertions, 21 deletions
| diff --git a/youtube_dl/extractor/youtube.py b/youtube_dl/extractor/youtube.py index bf4f4e139..77cd271ef 100644 --- a/youtube_dl/extractor/youtube.py +++ b/youtube_dl/extractor/youtube.py @@ -1269,37 +1269,57 @@ class YoutubeIE(YoutubeBaseInfoExtractor):                      sub_lang_list[sub_lang] = sub_formats                  return sub_lang_list +            def make_captions(sub_url, sub_langs): +                parsed_sub_url = compat_urllib_parse_urlparse(sub_url) +                caption_qs = compat_parse_qs(parsed_sub_url.query) +                captions = {} +                for sub_lang in sub_langs: +                    sub_formats = [] +                    for ext in self._SUBTITLE_FORMATS: +                        caption_qs.update({ +                            'tlang': [sub_lang], +                            'fmt': [ext], +                        }) +                        sub_url = compat_urlparse.urlunparse(parsed_sub_url._replace( +                            query=compat_urllib_parse_urlencode(caption_qs, True))) +                        sub_formats.append({ +                            'url': sub_url, +                            'ext': ext, +                        }) +                    captions[sub_lang] = sub_formats +                return captions + +            # New captions format as of 22.06.2017 +            player_response = args.get('player_response') +            if player_response and isinstance(player_response, compat_str): +                player_response = self._parse_json( +                    player_response, video_id, fatal=False) +                if player_response: +                    renderer = player_response['captions']['playerCaptionsTracklistRenderer'] +                    base_url = renderer['captionTracks'][0]['baseUrl'] +                    sub_lang_list = [] +                    for lang in renderer['translationLanguages']: +                        lang_code = lang.get('languageCode') +                        if lang_code: +                            sub_lang_list.append(lang_code) +                    return make_captions(base_url, sub_lang_list) +              # Some videos don't provide ttsurl but rather caption_tracks and              # caption_translation_languages (e.g. 20LmZk1hakA) +            # Does not used anymore as of 22.06.2017              caption_tracks = args['caption_tracks']              caption_translation_languages = args['caption_translation_languages']              caption_url = compat_parse_qs(caption_tracks.split(',')[0])['u'][0] -            parsed_caption_url = compat_urllib_parse_urlparse(caption_url) -            caption_qs = compat_parse_qs(parsed_caption_url.query) - -            sub_lang_list = {} +            sub_lang_list = []              for lang in caption_translation_languages.split(','):                  lang_qs = compat_parse_qs(compat_urllib_parse_unquote_plus(lang))                  sub_lang = lang_qs.get('lc', [None])[0] -                if not sub_lang: -                    continue -                sub_formats = [] -                for ext in self._SUBTITLE_FORMATS: -                    caption_qs.update({ -                        'tlang': [sub_lang], -                        'fmt': [ext], -                    }) -                    sub_url = compat_urlparse.urlunparse(parsed_caption_url._replace( -                        query=compat_urllib_parse_urlencode(caption_qs, True))) -                    sub_formats.append({ -                        'url': sub_url, -                        'ext': ext, -                    }) -                sub_lang_list[sub_lang] = sub_formats -            return sub_lang_list +                if sub_lang: +                    sub_lang_list.append(sub_lang) +            return make_captions(caption_url, sub_lang_list)          # An extractor error can be raise by the download process if there are          # no automatic captions but there are subtitles -        except (KeyError, ExtractorError): +        except (KeyError, IndexError, ExtractorError):              self._downloader.report_warning(err_msg)              return {} | 
