#!/usr/bin/python -u

import sys, getopt, dbus
from subprocess import Popen, PIPE

def main(argv):

    arg = 0
    while arg < len(argv):
        if argv[arg] in ("-h", "--help"):   show_help()
        elif argv[arg] == "status":       show_current_song()
        elif argv[arg] == "status-short": show_current_song_short()
        elif argv[arg] == "play":         perform_spotify_action("Play")
        elif argv[arg] == "pause":        perform_spotify_action("Pause")
        elif argv[arg] in ("toggle", "tog"):    perform_spotify_action("PlayPause")
        elif argv[arg] == "next":         perform_spotify_action("Next")
        elif argv[arg] == "prev":         perform_spotify_action("Previous")
        elif argv[arg] == "vu":     control_volume("+5%")
        elif argv[arg] == "vd":   control_volume("-5%")
        elif argv[arg] == "vol":
            arg+=1
            control_volume(argv[arg]+"%")

        arg+=1

def show_help():
    print ('\n  spotify-cli is a command line interface for Spotify on Linux\n\n' \
          '  usage:\n' \
          '    --help, -h\t\tshows help\n' \
          '    status\t\tshows status (currently played song name and artist)\n' \
          '    status-short\tshows status in a short way (cuts currently played song name and artist)\n' \
          '    play\t\tplays the song\n' \
          '    pause\t\tpauses the song\n' \
           '    toggle, tog\t\tplays or pauses the song (toggles a state)\n' \
          '    next\t\tplays the next song\n' \
          '    prev\t\tplays the previous song\n' \
          '    vu\t\t\tincreases sound volume\n' \
          '    vd\t\t\tdecreases sound volume\n'
          '    vol\t\t\tsets sound volume to specific value\n') \

def get_current_song():
    try:
        session_bus = dbus.SessionBus()
        spotify_bus = session_bus.get_object("org.mpris.MediaPlayer2.spotify", "/org/mpris/MediaPlayer2")
        spotify_properties = dbus.Interface(spotify_bus, "org.freedesktop.DBus.Properties")
        metadata = spotify_properties.Get("org.mpris.MediaPlayer2.Player", "Metadata")

        artist = metadata['xesam:artist'][0]
        title = metadata['xesam:title']
        return (artist, title)
    except:
        # we go here when spotify is turned off, not installed or we cannot access dbus
        return ("-", "-")

def is_spotify_available():
    artist, title = get_current_song()
    return not(artist == "-" and title == "-")

def show_current_song():
    if(is_spotify_available()):
        artist, title = get_current_song()
        print ("%s - %s" % (artist, title))
    else:
        print ("spotify is off")

def show_current_song_short():
    if(is_spotify_available()):
        artist, title = get_current_song()
        artist = artist[:15] + (artist[15:] and '...')
        title  = title[:10]  + (title[10:]  and '...')
        print ("%s - %s" % (artist, title))
    else:
      print ("spotify is off")

def perform_spotify_action(spotify_command):
    Popen('dbus-send --print-reply --dest=org.mpris.MediaPlayer2.spotify ' \
    '/org/mpris/MediaPlayer2 org.mpris.MediaPlayer2.Player."%s"' % spotify_command, shell=True, stdout=PIPE)

def get_sink_input():
    if is_spotify_available():
        curInput=-1
        proc = Popen('pactl list sink-inputs', shell=True, stdout=PIPE)
        for line in iter(proc.stdout.readline, b''):
            if "Sink Input" in line:
                curInput = int(line.split("#")[1].strip())
                continue
            elif "Spotify" in line:
                return curInput
    else:
        print ("spotify is off")            

def control_volume(volume_percent):
    Popen('pactl set-sink-input-volume %d "%s"' % (get_sink_input(), volume_percent), shell=True, stdout=PIPE)

if __name__ == "__main__":
    main(sys.argv[1:])
