From 2a7384a10876c5ea81ef4bce3d3968b5b9074a61 Mon Sep 17 00:00:00 2001 From: Josh Holtrop Date: Tue, 8 Nov 2016 22:12:27 -0500 Subject: [PATCH] tag-mp3s.py: clean up song titles and album names --- tag-mp3s.py | 60 ++++++++++++++++++++++++++++++++++++++++------------- 1 file changed, 46 insertions(+), 14 deletions(-) diff --git a/tag-mp3s.py b/tag-mp3s.py index 9dee0cb..6c631c8 100755 --- a/tag-mp3s.py +++ b/tag-mp3s.py @@ -6,6 +6,7 @@ import mutagen.id3 import mutagen.mp3 import os import sys +import re min_mp3s_for_album = 4 dry_run = False @@ -22,16 +23,21 @@ def walk_tree(base_dir, visit_function): def process_dir(path): mp3s = glob.glob("%s/*.mp3" % path) jpgs = glob.glob("%s/*.jpg" % path) + artwork_path = choose_artwork(mp3s, jpgs) + for mp3 in mp3s: + process_mp3(mp3, artwork_path) + +def choose_artwork(mp3s, jpgs): if len(mp3s) < min_mp3s_for_album: - return + return None if len(jpgs) == 0: sys.stderr.write("No album artwork found in %s\n" % path) - return + return None if len(jpgs) > 1: sys.stderr.write("Multiple album artwork files found in %s\n" % path) - return - for mp3 in mp3s: - add_artwork(mp3, jpgs[0]) + return None + return jpgs[0] + def read_file(fname): f = open(fname, "rb") @@ -39,17 +45,39 @@ def read_file(fname): f.close() return data -def add_artwork(mp3_path, jpg_path): +def clean_title(title): + new_title = re.sub(r'[\[\(]((explicit\s+)?album\s+version|explicit|clean)[\]\)]', '', title, flags = re.IGNORECASE) + new_title = re.sub(r'\s\s+', ' ', new_title) + return new_title.strip() + +def clean_tag(mp3, tagname): + if tagname in mp3: + tag = mp3[tagname] + if tag is not None: + orig_text = tag.text[0] + new_text = clean_title(orig_text) + if new_text != orig_text: + sys.stdout.write("Changing %s from \"%s\" to \"%s\"\n" % (tagname, orig_text, new_text)) + tag.text = [new_text] + return True + return False + +def process_mp3(mp3_path, artwork_path): mp3 = mutagen.mp3.MP3(mp3_path) current_tags = mp3.tags - apic_tags = [tag for tag in current_tags if tag == "APIC" or tag.startswith("APIC:")] - if len(apic_tags) >= 1: - return - print("Adding APIC tag to %s..." % mp3_path) - jpg_data = read_file(jpg_path) - apic = mutagen.id3.APIC(0, "image/jpeg", 0, "", jpg_data) - mp3.tags.add(apic) - if not dry_run: + changed = False + changed = clean_tag(mp3, "TIT2") or changed + changed = clean_tag(mp3, "TALB") or changed + if artwork_path is not None: + apic_tags = [tag for tag in current_tags if tag == "APIC" or tag.startswith("APIC:")] + if len(apic_tags) < 1: + print("Adding APIC tag to %s..." % mp3_path) + jpg_data = read_file(artwork_path) + apic = mutagen.id3.APIC(0, "image/jpeg", 0, "", jpg_data) + mp3.tags.add(apic) + changed = True + if changed and not dry_run: + sys.stdout.write("Writing %s\n" % mp3_path) mp3.save() def main(argv): @@ -59,7 +87,11 @@ def main(argv): if opt == '-d': base_dir = val elif opt == '-n': + global dry_run dry_run = True + if len(args) > 0: + sys.stderr.write("Usage: %s\n" % (sys.argv[0])) + return walk_tree(base_dir, process_dir) if __name__ == "__main__":