From fc8417a670286dd2658efa06cc4821b5cea245fb Mon Sep 17 00:00:00 2001 From: coderkun Date: Tue, 26 Jul 2016 22:45:30 +0200 Subject: [PATCH] clean-tags.py: add support for cleaning vorbis comments in FLAC files --- clean-tags.py | 68 ++++++++++++++++++++++++++++++++++++++++++++++++--- 1 file changed, 64 insertions(+), 4 deletions(-) diff --git a/clean-tags.py b/clean-tags.py index 13d4fea..a8ecd65 100755 --- a/clean-tags.py +++ b/clean-tags.py @@ -11,6 +11,7 @@ import logging import os from mutagen.id3 import ID3 +from mutagen.flac import FLAC from mutagen import MutagenError @@ -30,14 +31,17 @@ class TagCleaner: them. """ INDENTATION = " " - FILE_EXTENSIONS = ['.mp3'] + FILE_EXTENSIONS = ['.mp3', '.flac', '.ogg'] TAGS_ID3 = ['TALB', 'TDRC', 'TIT2', 'TPE1', 'TRCK'] + TAGS_VORBIS_COMMENTS = ['ALBUM', 'ARTIST', 'DATE', 'TITLE', 'TRACKNUMBER'] def __init__(self, folder): """Construct a new tag cleaner instancce.""" self._logger = logging.getLogger(__class__.__name__) self._dry = False + self._id3 = True + self._flac = True self._folder = folder self._files = [] self._read_files(folder) @@ -48,6 +52,16 @@ class TagCleaner: self._dry = dry + def set_id3(self, do): + """Set whether to clean ID3 tags or not.""" + self._id3 = do + + + def set_flac(self, do): + """Set whether to clean FLAC vorbis comments or not.""" + self._flac = do + + def clean_files(self): """Clean all found files.""" self._logger.info("Clean files") @@ -66,7 +80,7 @@ class TagCleaner: continue self._logger.debug("Found file \"%s\"", os.path.join(dirname, filename)) self._files.append(os.path.join(dirname, filename)) - self._logger.info("Found %d files".format(len(self._files))) + self._logger.info("Found %d files", len(self._files)) def _clean_file(self, filename): @@ -74,7 +88,11 @@ class TagCleaner: self._logger.info("Clean file \"%s\"", filename) if os.path.isfile(filename): # ID3 - self._clean_id3(filename) + if self._id3: + self._clean_id3(filename) + # FLAC + if self._flac: + self._clean_flac(filename) else: self._logger.info("Not a file: \"%s\"", filename) @@ -136,7 +154,44 @@ class TagCleaner: else: self._logger.info("Clean, nothing to do") except MutagenError as e: - self._logger.error("Cleaning of ID3 tags failed: %s", e) + self._logger.info("Cleaning of ID3 tags failed: %s", e) + + + def _clean_flac(self, filename): + """Clean FLAC vorbis comments.""" + self._logger.info("Clean FLAC vorbis comments") + try: + flac = FLAC(filename) + invalid_comments = {} + if flac.tags: + invalid_comments = self._clean_vorbis_comments(flac.tags) + # Delete comments + if invalid_comments: + for key in invalid_comments.keys(): + print("Delete", key) + del flac.tags[key] + if not self._dry: + flac.save() + print("File saved") + else: + print("File not saved (running in dry mode)") + else: + self._logger.info("Clean, nothing to do") + except MutagenError as e: + self._logger.info("Cleaning of FLAC vorbis comments failed: %s", e) + + + def _clean_vorbis_comments(self, comments): + invalid_comments = {} + for key, value in comments: + if key not in TagCleaner.TAGS_VORBIS_COMMENTS: + invalid_comments[key] = value + if invalid_comments: + print("Unwanted comments:") + for key in invalid_comments.keys(): + print("{}{}: {}".format(TagCleaner.INDENTATION, key, invalid_comments[key])) + + return invalid_comments @@ -147,7 +202,10 @@ if __name__ == "__main__": parser.add_argument('-d', '--dry', dest='dry', action='store_true', default=False, help="dry run, do not modify any file, just print information") parser.add_argument('-v', '--verbose', dest='verbosity', action='count', default=0, help="be verbose, show more information") parser.add_argument('-l', '--logfile', dest='logfile', help="specify name of logfile") + parser.add_argument('--no-id3', dest='id3', action='store_false', help="disable cleaning of ID3 tags") + parser.add_argument('--no-fac', dest='flac', action='store_false', help="disable cleaning of FLAC vorbis comments") parser.add_argument('folder', help="source folder to read audio files from") + parser.set_defaults(id3=True, flac=True) args = parser.parse_args() # Setup logging @@ -160,6 +218,8 @@ if __name__ == "__main__": # Create tag cleaner instance tag_cleaner = TagCleaner(args.folder) tag_cleaner.set_dry(args.dry) + tag_cleaner.set_id3(args.id3) + tag_cleaner.set_flac(args.flac) # Run action tag_cleaner.clean_files()