From 592e97e8550389e22b716eb33c30584aa3a8d656 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jaime=20Marqui=CC=81nez=20Ferra=CC=81ndiz?= Date: Sat, 18 Apr 2015 11:36:42 +0200 Subject: [PATCH] Postprocessors: use a list for the files that can be deleted We could only know if we had to delete the original file, but this system allows to specify us more files (like subtitles). --- test/test_YoutubeDL.py | 21 ++++++++---- youtube_dl/YoutubeDL.py | 13 +++---- youtube_dl/postprocessor/atomicparsley.py | 2 +- youtube_dl/postprocessor/common.py | 8 ++--- youtube_dl/postprocessor/execafterdownload.py | 2 +- youtube_dl/postprocessor/ffmpeg.py | 34 +++++++++---------- youtube_dl/postprocessor/metadatafromtitle.py | 2 +- youtube_dl/postprocessor/xattrpp.py | 4 +-- 8 files changed, 48 insertions(+), 38 deletions(-) diff --git a/test/test_YoutubeDL.py b/test/test_YoutubeDL.py index 652519831c..820e55ec2a 100644 --- a/test/test_YoutubeDL.py +++ b/test/test_YoutubeDL.py @@ -443,27 +443,36 @@ class SimplePP(PostProcessor): def run(self, info): with open(audiofile, 'wt') as f: f.write('EXAMPLE') - info['filepath'] - return False, info + return [info['filepath']], info - def run_pp(params): + def run_pp(params, PP): with open(filename, 'wt') as f: f.write('EXAMPLE') ydl = YoutubeDL(params) - ydl.add_post_processor(SimplePP()) + ydl.add_post_processor(PP()) ydl.post_process(filename, {'filepath': filename}) - run_pp({'keepvideo': True}) + run_pp({'keepvideo': True}, SimplePP) self.assertTrue(os.path.exists(filename), '%s doesn\'t exist' % filename) self.assertTrue(os.path.exists(audiofile), '%s doesn\'t exist' % audiofile) os.unlink(filename) os.unlink(audiofile) - run_pp({'keepvideo': False}) + run_pp({'keepvideo': False}, SimplePP) self.assertFalse(os.path.exists(filename), '%s exists' % filename) self.assertTrue(os.path.exists(audiofile), '%s doesn\'t exist' % audiofile) os.unlink(audiofile) + class ModifierPP(PostProcessor): + def run(self, info): + with open(info['filepath'], 'wt') as f: + f.write('MODIFIED') + return [], info + + run_pp({'keepvideo': False}, ModifierPP) + self.assertTrue(os.path.exists(filename), '%s doesn\'t exist' % filename) + os.unlink(filename) + def test_match_filter(self): class FilterYDL(YDL): def __init__(self, *args, **kwargs): diff --git a/youtube_dl/YoutubeDL.py b/youtube_dl/YoutubeDL.py index 6ac85f4e7e..8d8b146b20 100755 --- a/youtube_dl/YoutubeDL.py +++ b/youtube_dl/YoutubeDL.py @@ -1488,15 +1488,16 @@ def post_process(self, filename, ie_info): for pp in pps_chain: old_filename = info['filepath'] try: - keep_video, info = pp.run(info) + files_to_delete, info = pp.run(info) except PostProcessingError as e: self.report_error(e.msg) - if keep_video is False and not self.params.get('keepvideo', False): - try: + if files_to_delete and not self.params.get('keepvideo', False): + for old_filename in files_to_delete: self.to_screen('Deleting original file %s (pass -k to keep)' % old_filename) - os.remove(encodeFilename(old_filename)) - except (IOError, OSError): - self.report_warning('Unable to remove downloaded video file') + try: + os.remove(encodeFilename(old_filename)) + except (IOError, OSError): + self.report_warning('Unable to remove downloaded original file') def _make_archive_id(self, info_dict): # Future-proof against any change in case diff --git a/youtube_dl/postprocessor/atomicparsley.py b/youtube_dl/postprocessor/atomicparsley.py index a5dfc136af..e4e198695c 100644 --- a/youtube_dl/postprocessor/atomicparsley.py +++ b/youtube_dl/postprocessor/atomicparsley.py @@ -59,4 +59,4 @@ def run(self, info): os.remove(encodeFilename(filename)) os.rename(encodeFilename(temp_filename), encodeFilename(filename)) - return True, info + return [], info diff --git a/youtube_dl/postprocessor/common.py b/youtube_dl/postprocessor/common.py index ef9fdfa19a..3b0e8ddd8b 100644 --- a/youtube_dl/postprocessor/common.py +++ b/youtube_dl/postprocessor/common.py @@ -42,14 +42,14 @@ def run(self, information): one has an extra field called "filepath" that points to the downloaded file. - This method returns a tuple, the first element of which describes - whether the original file should be kept (i.e. not deleted - None for - no preference), and the second of which is the updated information. + This method returns a tuple, the first element is a list of the files + that can be deleted, and the second of which is the updated + information. In addition, this method may raise a PostProcessingError exception if post processing fails. """ - return None, information # by default, keep file and do nothing + return [], information # by default, keep file and do nothing def try_utime(self, path, atime, mtime, errnote='Cannot update utime of file'): try: diff --git a/youtube_dl/postprocessor/execafterdownload.py b/youtube_dl/postprocessor/execafterdownload.py index 75c0f7bbe8..3414375751 100644 --- a/youtube_dl/postprocessor/execafterdownload.py +++ b/youtube_dl/postprocessor/execafterdownload.py @@ -25,4 +25,4 @@ def run(self, information): raise PostProcessingError( 'Command returned error code %d' % retCode) - return None, information # by default, keep file and do nothing + return [], information diff --git a/youtube_dl/postprocessor/ffmpeg.py b/youtube_dl/postprocessor/ffmpeg.py index 4c4a038f9c..4cdbfce63e 100644 --- a/youtube_dl/postprocessor/ffmpeg.py +++ b/youtube_dl/postprocessor/ffmpeg.py @@ -267,7 +267,7 @@ def run(self, information): if (new_path == path or (self._nopostoverwrites and os.path.exists(encodeFilename(new_path)))): self._downloader.to_screen('[youtube] Post-process file %s exists, skipping' % new_path) - return True, information + return [], information try: self._downloader.to_screen('[' + self.basename + '] Destination: ' + new_path) @@ -285,7 +285,7 @@ def run(self, information): errnote='Cannot update utime of audio file') information['filepath'] = new_path - return False, information + return [path], information class FFmpegVideoConvertorPP(FFmpegPostProcessor): @@ -299,13 +299,13 @@ def run(self, information): outpath = prefix + sep + self._preferedformat if information['ext'] == self._preferedformat: self._downloader.to_screen('[ffmpeg] Not converting video file %s - already is in target format %s' % (path, self._preferedformat)) - return True, information + return [], information self._downloader.to_screen('[' + 'ffmpeg' + '] Converting video from %s to %s, Destination: ' % (information['ext'], self._preferedformat) + outpath) self.run_ffmpeg(path, outpath, []) information['filepath'] = outpath information['format'] = self._preferedformat information['ext'] = self._preferedformat - return False, information + return [path], information class FFmpegEmbedSubtitlePP(FFmpegPostProcessor): @@ -505,11 +505,11 @@ def _conver_lang_code(cls, code): def run(self, information): if information['ext'] != 'mp4': self._downloader.to_screen('[ffmpeg] Subtitles can only be embedded in mp4 files') - return True, information + return [], information subtitles = information.get('requested_subtitles') if not subtitles: self._downloader.to_screen('[ffmpeg] There aren\'t any subtitles to embed') - return True, information + return [], information sub_langs = list(subtitles.keys()) filename = information['filepath'] @@ -535,7 +535,7 @@ def run(self, information): os.remove(encodeFilename(filename)) os.rename(encodeFilename(temp_filename), encodeFilename(filename)) - return True, information + return [], information class FFmpegMetadataPP(FFmpegPostProcessor): @@ -561,7 +561,7 @@ def run(self, info): if not metadata: self._downloader.to_screen('[ffmpeg] There isn\'t any metadata to add') - return True, info + return [], info filename = info['filepath'] temp_filename = prepend_extension(filename, 'temp') @@ -578,7 +578,7 @@ def run(self, info): self.run_ffmpeg(filename, temp_filename, options) os.remove(encodeFilename(filename)) os.rename(encodeFilename(temp_filename), encodeFilename(filename)) - return True, info + return [], info class FFmpegMergerPP(FFmpegPostProcessor): @@ -587,7 +587,7 @@ def run(self, info): args = ['-c', 'copy', '-map', '0:v:0', '-map', '1:a:0'] self._downloader.to_screen('[ffmpeg] Merging formats into "%s"' % filename) self.run_ffmpeg_multiple_files(info['__files_to_merge'], filename, args) - return True, info + return [], info class FFmpegAudioFixPP(FFmpegPostProcessor): @@ -602,14 +602,14 @@ def run(self, info): os.remove(encodeFilename(filename)) os.rename(encodeFilename(temp_filename), encodeFilename(filename)) - return True, info + return [], info class FFmpegFixupStretchedPP(FFmpegPostProcessor): def run(self, info): stretched_ratio = info.get('stretched_ratio') if stretched_ratio is None or stretched_ratio == 1: - return True, info + return [], info filename = info['filepath'] temp_filename = prepend_extension(filename, 'temp') @@ -621,13 +621,13 @@ def run(self, info): os.remove(encodeFilename(filename)) os.rename(encodeFilename(temp_filename), encodeFilename(filename)) - return True, info + return [], info class FFmpegFixupM4aPP(FFmpegPostProcessor): def run(self, info): if info.get('container') != 'm4a_dash': - return True, info + return [], info filename = info['filepath'] temp_filename = prepend_extension(filename, 'temp') @@ -639,7 +639,7 @@ def run(self, info): os.remove(encodeFilename(filename)) os.rename(encodeFilename(temp_filename), encodeFilename(filename)) - return True, info + return [], info class FFmpegSubtitlesConvertorPP(FFmpegPostProcessor): @@ -656,7 +656,7 @@ def run(self, info): new_format = 'webvtt' if subs is None: self._downloader.to_screen('[ffmpeg] There aren\'t any subtitles to convert') - return True, info + return [], info self._downloader.to_screen('[ffmpeg] Converting subtitles') for lang, sub in subs.items(): ext = sub['ext'] @@ -676,4 +676,4 @@ def run(self, info): 'data': f.read(), } - return True, info + return [], info diff --git a/youtube_dl/postprocessor/metadatafromtitle.py b/youtube_dl/postprocessor/metadatafromtitle.py index 5019433d3d..a56077f206 100644 --- a/youtube_dl/postprocessor/metadatafromtitle.py +++ b/youtube_dl/postprocessor/metadatafromtitle.py @@ -44,4 +44,4 @@ def run(self, info): info[attribute] = value self._downloader.to_screen('[fromtitle] parsed ' + attribute + ': ' + value) - return True, info + return [], info diff --git a/youtube_dl/postprocessor/xattrpp.py b/youtube_dl/postprocessor/xattrpp.py index f6c63fe975..0cba99fc31 100644 --- a/youtube_dl/postprocessor/xattrpp.py +++ b/youtube_dl/postprocessor/xattrpp.py @@ -105,8 +105,8 @@ def write_xattr(path, key, value): byte_value = value.encode('utf-8') write_xattr(filename, xattrname, byte_value) - return True, info + return [], info except (subprocess.CalledProcessError, OSError): self._downloader.report_error("This filesystem doesn't support extended attributes. (You may have to enable them in your /etc/fstab)") - return False, info + return [], info