#!/usr/bin/env python3
# id3-lyrics - read and write lyrics tags
import sys
import getopt
import mutagen.mp3
import mutagen.id3
from nullroute.core import Core

def usage():
    print("Usage:")
    print("    import: lyrics -i [-f lyrics_file] audio_file")
    print("    export: lyrics -e [-f lyrics_file] audio_file")
    print("    remove: lyrics -x audio_file")

def to_crlf(s):
    return s.replace("\r\n", "\n").replace("\n", "\r\n")

def from_crlf(s):
    return s.replace("\r\n", "\n")

def write_id3(tag, lyrics, lang="eng"):
    atom = "USLT::'%s'" % lang
    if lyrics is None:
        if atom in tag:
            del tag[atom]
    else:
        tag[atom] = mutagen.id3.USLT()
        tag[atom].text = lyrics
        tag[atom].encoding = 1
        tag[atom].lang = lang
        tag[atom].desc = ""

def read_id3(tag):
    for key in tag.keys():
        if key.startswith("USLT:"):
            Core.debug("returning lyrics tag %r", key)
            return tag[key].text
    return None

def strip_id3(tag):
    for key in [*tag.keys()]:
        if key.startswith("USLT:"):
            Core.debug("removing lyrics tag %r", key)
            del tag[key]

mode = None
lyricsfile = None
verbose = False

try:
    options, audiofiles = getopt.gnu_getopt(sys.argv[1:], "ef:iovx")
except getopt.GetoptError as e:
    Core.err("%s", e)
    usage()
    sys.exit(2)

for opt, value in options:
    if None: pass
    elif opt == "-e": mode = "output"
    elif opt == "-f": lyricsfile = value
    elif opt == "-i": mode = "input"
    elif opt == "-o": mode = "output"
    elif opt == "-v": verbose = True
    elif opt == "-x": mode = "kill"

if len(audiofiles) == 0:
    Core.die("no .mp3 files specified")

if mode == "input":
    if lyricsfile is None:
        f = sys.stdin
    else:
        f = open(lyricsfile, "r")
    lyrics = f.read()
    lyrics = from_crlf(lyrics)
    for path in audiofiles:
        Core.info("writing %s", path)
        file = mutagen.mp3.MP3(path)
        strip_id3(file)
        write_id3(file, lyrics)
        file.save()
elif mode == "output":
    if lyricsfile is None:
        f = sys.stdout
    else:
        f = open(lyricsfile, "w")
    for path in audiofiles:
        file = mutagen.mp3.MP3(path)
        lyrics = read_id3(file)
        if lyrics:
            lyrics = from_crlf(lyrics)
            sys.stdout.write(lyrics)
elif mode == "kill":
    for path in audiofiles:
        Core.info("writing %s", path)
        file = mutagen.mp3.MP3(path)
        strip_id3(file)
        file.save()
else:
    Core.die("BUG: bad mode %r" % mode)
