71 lines
2.1 KiB
Python
Executable file
71 lines
2.1 KiB
Python
Executable file
#!/usr/bin/env python3
|
|
# -*- coding: utf-8 -*-
|
|
|
|
from fuzzywuzzy import fuzz, process
|
|
from mutagen.easyid3 import EasyID3
|
|
from mutagen.id3 import ID3NoHeaderError
|
|
import os
|
|
from os.path import basename, normpath, splitext
|
|
import sys
|
|
|
|
|
|
def eprint(*args, **kwargs):
|
|
print(*args, file=sys.stderr, **kwargs)
|
|
|
|
|
|
def filename(f):
|
|
return splitext(normpath(basename(f)))[0]
|
|
|
|
|
|
dirs = []
|
|
for d in sys.argv[1:]:
|
|
if not os.path.isdir(d):
|
|
eprint("Error: Cannot open {}: not a directory".format(d))
|
|
sys.exit(1)
|
|
dirs += [d]
|
|
|
|
for d in dirs:
|
|
# Get first level file list
|
|
(root, _, files) = next(os.walk(d))
|
|
dir_artist = filename(d)
|
|
|
|
for f in files:
|
|
f = os.path.join(root, f)
|
|
name = filename(f)
|
|
name_parts = name.split(" - ")
|
|
file_artist = name_parts[0]
|
|
fuzzy_artist = process.extractOne(dir_artist, name_parts, scorer=fuzz.token_sort_ratio)
|
|
|
|
if len(name_parts) < 2:
|
|
eprint("Error: No title found for {}".format(f))
|
|
continue
|
|
|
|
file_title = name_parts[1]
|
|
|
|
if dir_artist != file_artist:
|
|
eprint("""Error: Artist name mismatch between folder and file: {}
|
|
Fuzzy score = {:3d}, artist = {}""".format(f, fuzzy_artist[1], fuzzy_artist[0]))
|
|
# Test for common artist name patterns
|
|
if fuzzy_artist[1] < 90:
|
|
r = fuzz.ratio(dir_artist, "the " + fuzzy_artist[0])
|
|
if True: # r >= 95:
|
|
eprint(" Fuzzy match r={} for: {}".format(
|
|
r,
|
|
"the " + fuzzy_artist[0]))
|
|
continue
|
|
|
|
try:
|
|
id3 = EasyID3(f)
|
|
except ID3NoHeaderError:
|
|
id3 = EasyID3()
|
|
if id3 is None:
|
|
eprint("Error: cannot open {} for tagging".format(f))
|
|
continue
|
|
|
|
if "artist" not in id3.keys():
|
|
id3["artist"] = file_artist
|
|
print("Artist set to {}".format(file_artist))
|
|
if "title" not in id3.keys():
|
|
id3["title"] = file_title
|
|
print("Title set to {}".format(file_title))
|
|
# id3.save(f)
|