diff --git a/README.md b/README.md index 9abf993b61..b1068421be 100644 --- a/README.md +++ b/README.md @@ -594,15 +594,17 @@ Then simply run `make`. You can also run `make yt-dlp` instead to compile only t (Alias: --write-automatic-subs) --no-write-auto-subs Do not write auto-generated subtitles (default) (Alias: --no-write-automatic-subs) - --all-subs Download all the available subtitles of the - video --list-subs List all available subtitles for the video --sub-format FORMAT Subtitle format, accepts formats preference, for example: "srt" or "ass/srt/best" - --sub-langs LANGS Languages of the subtitles to download - (optional) separated by commas, use --list- - subs for available language tags + --sub-langs LANGS Languages of the subtitles to download (can + be regex) or "all" separated by commas. + (Eg: --sub-langs en.*,ja) You can prefix + the language code with a "-" to exempt it + from the requested languages. (Eg: --sub- + langs all,-live_chat) Use --list-subs for a + list of available language tags ## Authentication Options: -u, --username USERNAME Login with this account ID @@ -1257,6 +1259,7 @@ These are all the deprecated options and the current alternative to achieve the -t, --title -o "%(title)s-%(id)s.%(ext)s" -l, --literal -o accepts literal names --all-formats -f all + --all-subs --sub-langs all --write-subs --autonumber-size NUMBER Use string formatting. Eg: %(autonumber)03d --metadata-from-title FORMAT --parse-metadata "%(title)s:FORMAT" --prefer-avconv avconv is no longer officially supported (Alias: --no-prefer-ffmpeg) diff --git a/test/test_YoutubeDL.py b/test/test_YoutubeDL.py index b910a26a88..405db9058f 100644 --- a/test/test_YoutubeDL.py +++ b/test/test_YoutubeDL.py @@ -601,6 +601,26 @@ class TestYoutubeDL(unittest.TestCase): self.assertTrue(subs) self.assertEqual(set(subs.keys()), set(['es', 'fr'])) + result = get_info({'writesubtitles': True, 'subtitleslangs': ['all', '-en']}) + subs = result['requested_subtitles'] + self.assertTrue(subs) + self.assertEqual(set(subs.keys()), set(['es', 'fr'])) + + result = get_info({'writesubtitles': True, 'subtitleslangs': ['en', 'fr', '-en']}) + subs = result['requested_subtitles'] + self.assertTrue(subs) + self.assertEqual(set(subs.keys()), set(['fr'])) + + result = get_info({'writesubtitles': True, 'subtitleslangs': ['-en', 'en']}) + subs = result['requested_subtitles'] + self.assertTrue(subs) + self.assertEqual(set(subs.keys()), set(['en'])) + + result = get_info({'writesubtitles': True, 'subtitleslangs': ['e.+']}) + subs = result['requested_subtitles'] + self.assertTrue(subs) + self.assertEqual(set(subs.keys()), set(['es', 'en'])) + result = get_info({'writesubtitles': True, 'writeautomaticsub': True, 'subtitleslangs': ['es', 'pt']}) subs = result['requested_subtitles'] self.assertTrue(subs) diff --git a/yt_dlp/YoutubeDL.py b/yt_dlp/YoutubeDL.py index 7cda3fc8f2..29931474d5 100644 --- a/yt_dlp/YoutubeDL.py +++ b/yt_dlp/YoutubeDL.py @@ -244,11 +244,15 @@ class YoutubeDL(object): writedesktoplink: Write a Linux internet shortcut file (.desktop) writesubtitles: Write the video subtitles to a file writeautomaticsub: Write the automatically generated subtitles to a file - allsubtitles: Downloads all the subtitles of the video + allsubtitles: Deprecated - Use subtitlelangs = ['all'] + Downloads all the subtitles of the video (requires writesubtitles or writeautomaticsub) listsubtitles: Lists all available subtitles for the video subtitlesformat: The format code for subtitles - subtitleslangs: List of languages of the subtitles to download + subtitleslangs: List of languages of the subtitles to download (can be regex). + The list may contain "all" to refer to all the available + subtitles. The language can be prefixed with a "-" to + exclude it from the requested languages. Eg: ['all', '-live_chat'] keepvideo: Keep the video file after post-processing daterange: A DateRange object, download only if the upload_date is in the range. skip_download: Skip the actual download of the video file @@ -2038,15 +2042,28 @@ class YoutubeDL(object): available_subs): return None + all_sub_langs = available_subs.keys() if self.params.get('allsubtitles', False): - requested_langs = available_subs.keys() + requested_langs = all_sub_langs + elif self.params.get('subtitleslangs', False): + requested_langs = set() + for lang in self.params.get('subtitleslangs'): + if lang == 'all': + requested_langs.update(all_sub_langs) + continue + discard = lang[0] == '-' + if discard: + lang = lang[1:] + current_langs = filter(re.compile(lang + '$').match, all_sub_langs) + if discard: + for lang in current_langs: + requested_langs.discard(lang) + else: + requested_langs.update(current_langs) + elif 'en' in available_subs: + requested_langs = ['en'] else: - if self.params.get('subtitleslangs', False): - requested_langs = self.params.get('subtitleslangs') - elif 'en' in available_subs: - requested_langs = ['en'] - else: - requested_langs = [list(available_subs.keys())[0]] + requested_langs = [list(all_sub_langs)[0]] formats_query = self.params.get('subtitlesformat', 'best') formats_preference = formats_query.split('/') if formats_query else [] diff --git a/yt_dlp/options.py b/yt_dlp/options.py index fef1e4b152..a16604b733 100644 --- a/yt_dlp/options.py +++ b/yt_dlp/options.py @@ -548,7 +548,7 @@ def parseOpts(overrideArguments=None): subtitles.add_option( '--all-subs', action='store_true', dest='allsubtitles', default=False, - help='Download all the available subtitles of the video') + help=optparse.SUPPRESS_HELP) subtitles.add_option( '--list-subs', action='store_true', dest='listsubtitles', default=False, @@ -561,7 +561,10 @@ def parseOpts(overrideArguments=None): '--sub-langs', '--srt-langs', action='callback', dest='subtitleslangs', metavar='LANGS', type='str', default=[], callback=_comma_separated_values_options_callback, - help='Languages of the subtitles to download (optional) separated by commas, use --list-subs for available language tags') + help=( + 'Languages of the subtitles to download (can be regex) or "all" separated by commas. (Eg: --sub-langs en.*,ja) ' + 'You can prefix the language code with a "-" to exempt it from the requested languages. (Eg: --sub-langs all,-live_chat) ' + 'Use --list-subs for a list of available language tags')) downloader = optparse.OptionGroup(parser, 'Download Options') downloader.add_option(