import argparse import requests import json as jsn import urllib.request import numpy as np import imgcat from PIL import Image import sys import time import traceback ''' create file called secrets in same folder as spot.py with app token on line 1 and refresh token on line 2 ''' def spotAuth(): f = open(sys.path[0]+"/secrets", "r") appToken = f.readline()[:-1] refreshToken = f.readline()[:-1] tokenURL = "https://accounts.spotify.com/api/token" headers = {"Authorization": "Basic "+appToken} payload = {"grant_type": "refresh_token", "refresh_token": refreshToken} r = requests.post(tokenURL, headers=headers, data=payload) json = r.json() accessToken = json["access_token"] return accessToken def spotDevice(headers, caller): r = requests.get("https://api.spotify.com/v1/me/player/devices", headers=headers) if r.status_code != 200: print('Invalid permissions!') quit() json = r.json() deviceid = None if len(json["devices"]) == 0: print("No playback devices") quit() elif len(json["devices"]) == 1: deviceid = json["devices"][0]["id"] devicename = json["devices"][0]["name"] if caller == "dev": print("\033[1m\033[92m"+devicename+"\033[0m is only device.") quit() elif caller == "vol" or caller == "prev" or caller == "next" or caller == "np" or caller == "play": for i in json["devices"]: if i["is_active"] == True: deviceid = i["id"] devicename = i["name"] if deviceid == None: print("No active device, defaulting to 0") deviceid = json["devices"][0]["id"] devicename = json["devices"][0]["name"] elif caller == "dev": j = 0 devicedict = {} for i in json["devices"]: if i["is_active"] == False: print("["+str(j)+"] "+i["name"]) devicedict.update( {j: [i["name"], i["id"]]}) j += 1 choice = input("Choose device: ") try: choice = int(choice) except: quit() deviceid = devicedict[choice][1] devicename = devicedict[choice][0] else: for i in range(0,len(json["devices"])): print("["+str(i)+"] "+json["devices"][i]["name"]) choice = input("Choose device: ") try: choice = int(choice) except: quit() deviceid = json["devices"][choice]["id"] devicename = json["devices"][choice]["name"] devicedict = {} devicedict.update( {"deviceid": deviceid}) devicedict.update( {"devicename": devicename}) return devicedict def spotSK(seekTime): accessToken = spotAuth() headers = {"Authorization": "Bearer "+accessToken} r = requests.get("https://api.spotify.com/v1/me/player/currently-playing", headers=headers) if r.status_code == 204: print("Nothing playing") quit() elif r.status_code != 200: print("Error: HTTP"+str(r.status_code)) quit() json = r.json() durationMS = int(json["item"]["duration_ms"]) seekMS = durationMS*(seekTime/4) seekMS = round(seekMS) r = requests.put("https://api.spotify.com/v1/me/player/seek?position_ms="+str(seekMS), headers=headers) if r.status_code == 204: print("Seeking to "+str((seekMS/1000)/60)+" minutes") else: print("Error: HTTP"+str(r.status_code)) return r.status_code def spotNP(imgcatBool, timeBool): accessToken = spotAuth() headers = {"Authorization": "Bearer "+accessToken} dev = spotDevice(headers, "np") devicename = dev["devicename"] r = requests.get("https://api.spotify.com/v1/me/player/currently-playing", headers=headers) if r.status_code == 204: print("Nothing playing") quit() elif r.status_code != 200: print("Error: HTTP"+str(r.status_code)) quit() try: json = r.json() playing = json["is_playing"] except: playing = False if playing == False: text = "paused" elif playing == True: text = "playing" title = json["item"]["name"] artist = json["item"]["album"]["artists"][0]["name"] imgurl = json["item"]["album"]["images"][1]["url"] durationSec = (json["item"]["duration_ms"])/1000 currentSec = (json["progress_ms"])/1000 print("\033[95m\033[1m"+title+"\033[0m by ", end='') print("\033[94m\033[1m"+artist+"\033[0m is "+text+" on ", end='') print("\033[92m\033[1m"+devicename+"\033[0m") if (imgcatBool): im = np.asarray(Image.open(urllib.request.urlopen(imgurl))) time.sleep(1) imgcat.imgcat(im) if (timeBool): print(str(round(currentSec//60))+":"+(str(round(currentSec%60))).zfill(2)+"/"+str(round(durationSec//60))+":"+(str(round(durationSec%60)).zfill(2))) return r.status_code def spotSE(context, query): print(query) accessToken = spotAuth() headers = {"Authorization": "Bearer "+accessToken} payload = {'type': context, 'q': query} r = requests.get("https://api.spotify.com/v1/search", params=payload, headers=headers) if r.status_code == 204: print("No results") quit() elif r.status_code != 200: print("Error: HTTP"+str(r.status_code)) quit() json = r.json() try: if context == "album": uri = json["albums"]["items"][0]["uri"] name = json["albums"]["items"][0]["name"] elif context == "track": uri = json["tracks"]["items"][0]["uri"] name = json["tracks"]["items"][0]["name"] except: print("Search returned no results") quit() dev = spotDevice(headers, "search") if context == "album": payload = {"context_uri": uri} else: payload = {"uris": [uri]} r = requests.put("https://api.spotify.com/v1/me/player/play?device_id="+dev["deviceid"], headers=headers, data=jsn.dumps(payload)) if r.status_code == 204: print("Playing "+context+"\033[1m\033[95m "+name+"\033[0m on \033[1m\033[92m"+dev["devicename"]+"\033[0m.") else: print("Unable to play \033[1m\033[95m"+name+"\033[0m.") return r.status_code def spotSF(): accessToken = spotAuth() headers = {"Authorization": "Bearer "+accessToken} r = requests.get("https://api.spotify.com/v1/me/player/currently-playing", headers=headers) if r.status_code == 204: print("No active playback session") quit() elif r.status_code != 200: print("Error: HTTP"+str(r.status_code)) quit() r = requests.get("https://api.spotify.com/v1/me/player", headers=headers) json = r.json() shuf = json["shuffle_state"] if shuf == True: shuf = "false" elif shuf == False: shuf = "true" r = requests.put("https://api.spotify.com/v1/me/player/shuffle?state="+shuf, headers=headers) return r.status_code def spotRE(): accessToken = spotAuth() headers = {"Authorization": "Bearer "+accessToken} r = requests.get("https://api.spotify.com/v1/me/player/currently-playing", headers=headers) if r.status_code == 204: print("No active playback session") quit() elif r.status_code != 200: print("Error: HTTP"+str(r.status_code)) quit() r = requests.get("https://api.spotify.com/v1/me/player", headers=headers) json = r.json() rep = json["repeat_state"] if rep == "context": rep = "off" elif rep == "off": rep = "context" else: rep = "off" r = requests.put("https://api.spotify.com/v1/me/player/repeat?state="+rep, headers=headers) if r.status_code == 204: r = requests.get("https://api.spotify.com/v1/me/player", headers=headers) json = r.json() currep = json["repeat_state"] else: print("Unable to toggle repeat.") return r.status_code def spotPR(): accessToken = spotAuth() headers = {"Authorization": "Bearer "+accessToken} r = requests.get("https://api.spotify.com/v1/me/player/currently-playing", headers=headers) if r.status_code == 204: print("No active playback session") quit() elif r.status_code != 200: print("Error: HTTP"+str(r.status_code)) quit() json = r.json() trackname = json["item"]["name"] trackid = json["item"]["id"] dev = spotDevice(headers, "prev") r = requests.post("https://api.spotify.com/v1/me/player/previous", headers=headers) if r.status_code == 204: time.sleep(0.5) r = requests.get("https://api.spotify.com/v1/me/player/currently-playing", headers=headers) if r.status_code == 204: print("No active playback session") quit() elif r.status_code != 200: print("Error: HTTP"+str(r.status_code)) quit() json = r.json() trackname = json["item"]["name"] trackid = json["item"]["id"] else: print("Unable to play \033[1m\033[95m"+trackname+"\033[0m.") return r.status_code def spotNE(): accessToken = spotAuth() headers = {"Authorization": "Bearer "+accessToken} r = requests.get("https://api.spotify.com/v1/me/player/currently-playing", headers=headers) if r.status_code == 204: print("No active playback session") quit() elif r.status_code != 200: print("Error: HTTP"+str(r.status_code)) quit() json = r.json() trackname = json["item"]["name"] trackid = json["item"]["id"] dev = spotDevice(headers, "next") r = requests.post("https://api.spotify.com/v1/me/player/next", headers=headers) if r.status_code == 204: time.sleep(0.5) r = requests.get("https://api.spotify.com/v1/me/player/currently-playing", headers=headers) if r.status_code == 204: print("No active playback session") quit() elif r.status_code != 200: print("Error: HTTP"+str(r.status_code)) quit() json = r.json() trackname = json["item"]["name"] trackid = json["item"]["id"] else: print("Unable to play \033[1m\033[95m"+trackname+"\033[0m.") return r.status_code def spotPP(): accessToken = spotAuth() headers = {"Authorization": "Bearer "+accessToken} dev = spotDevice(headers, "play") r = requests.get("https://api.spotify.com/v1/me/player", headers=headers) try: json = r.json() playing = json["is_playing"] except: playing = False if playing == False: r = requests.put("https://api.spotify.com/v1/me/player/play?device_id="+dev["deviceid"], headers=headers) if r.status_code == 204: time.sleep(0.5) r = requests.get("https://api.spotify.com/v1/me/player/currently-playing", headers=headers) if r.status_code == 204: quit() elif r.status_code != 200: print("Error: HTTP"+str(r.status_code)) quit() json = r.json() trackname = json["item"]["name"] trackid = json["item"]["id"] elif playing == True: r = requests.put("https://api.spotify.com/v1/me/player/pause?device_id="+dev["deviceid"], headers=headers) if r.status_code == 204: r = requests.get("https://api.spotify.com/v1/me/player/currently-playing", headers=headers) if r.status_code == 204: quit() elif r.status_code != 200: quit() json = r.json() trackname = json["item"]["name"] trackid = json["item"]["id"] return "Success" def spotLS(): accessToken = spotAuth() headers = {"Authorization": "Bearer "+accessToken} r = requests.get("https://api.spotify.com/v1/me/player/currently-playing", headers=headers) if r.status_code == 204: print("Nothing playing") quit() elif r.status_code != 200: print("Error: HTTP"+str(r.status_code)) quit() json = r.json() trackname = json["item"]["name"] trackid = json["item"]["id"] headers = {"Authorization": "Bearer "+accessToken, "Accept": "application/json", "Content-Type": "application/json"} r = requests.put("https://api.spotify.com/v1/me/tracks?ids="+trackid, headers=headers) if r.status_code == 200: print("Added \033[1m\033[95m"+json["item"]["name"]+"\033[0m to Liked Songs") else: print("An error occured, fun") return r.status_code def spotRL(): accessToken = spotAuth() headers = {"Authorization": "Bearer "+accessToken} r = requests.get("https://api.spotify.com/v1/me/player/currently-playing", headers=headers) if r.status_code == 204: print("Nothing playing") quit() elif r.status_code != 200: print("Error: HTTP"+str(r.status_code)) quit() json = r.json() trackname = json["item"]["name"] trackid = json["item"]["id"] headers = {"Authorization": "Bearer "+accessToken, "Accept": "application/json", "Content-Type": "application/json"} r = requests.delete("https://api.spotify.com/v1/me/tracks?ids="+trackid, headers=headers) if r.status_code == 200: print("Removed \033[1m\033[95m"+json["item"]["name"]+"\033[0m from Liked Songs") else: print("An error occured, fun") def spotAP(): accessToken = spotAuth() headers = {"Authorization": "Bearer "+accessToken} r = requests.get("https://api.spotify.com/v1/me/player/currently-playing", headers=headers) if r.status_code == 204: print("Nothing playing") quit() elif r.status_code != 200: print("Error: HTTP"+str(r.status_code)) quit() json = r.json() print("Add \033[1m\033[95m"+json["item"]["name"]+"\033[0m to:") trackname = json["item"]["name"] trackuri = json["item"]["uri"] trackuri.replace(":", "%3A") r = requests.get("https://api.spotify.com/v1/me", headers=headers) json = r.json() userid = json["id"] r = requests.get("https://api.spotify.com/v1/me/playlists?limit=50", headers=headers) json = r.json() j = 0 playdict = {} for i in json["items"]: if userid == i["owner"]["display_name"]: print("["+str(j)+"] "+i["name"]) playdict.update( {j: [i["name"], i["id"]]}) j += 1 elif i["collaborative"] == True: print("["+str(j)+"] "+i["name"]) playdict.update( {j: [i["name"], i["id"]]}) j += 1 choice = input("Select Playlist: ") try: choice = int(choice) except: quit() playlistid = playdict[choice][1] playlistname = playdict[choice][0] headers = {"Authorization": "Bearer "+accessToken, "Accept": "application/json", "Content-Type": "application/json"} r = requests.post("https://api.spotify.com/v1/playlists/"+playlistid+"/tracks?uris="+trackuri, headers=headers) if r.status_code == 201: print("Successfully added \033[1m\033[95m"+trackname+"\033[0m to \033[1m\033[96m"+playlistname+"\033[0m") else: print("Unable to add song to specified playlist. Do you have access to do so?") return r.status_code def spotPD(): accessToken = spotAuth() headers = {"Authorization": "Bearer "+accessToken} dev = spotDevice(headers, "dev") payload = {"device_ids":[dev["deviceid"]]} r = requests.put("https://api.spotify.com/v1/me/player", headers=headers, data=jsn.dumps(payload)) if r.status_code == 204: time.sleep(0.5) r = requests.get("https://api.spotify.com/v1/me/player/currently-playing", headers=headers) if r.status_code == 204: print("No active playback session") quit() elif r.status_code != 200: print("Error: HTTP"+str(r.status_code)) quit() json = r.json() trackname = json["item"]["name"] trackid = json["item"]["id"] print("Playing \033[1m\033[95m"+trackname+"\033[0m on \033[1m\033[92m"+dev["devicename"]+"\033[0m.") elif r.status_code == 202: time.sleep(2) r = requests.get("https://api.spotify.com/v1/me/player/currently-playing", headers=headers) if r.status_code == 204: print("No active playback session") quit() elif r.status_code != 200: print("Error: HTTP"+str(r.status_code)) quit() json = r.json() trackname = json["item"]["name"] trackid = json["item"]["id"] print("Playing \033[1m\033[95m"+trackname+"\033[0m on \033[1m\033[92m"+dev["devicename"]+"\033[0m.") else: print(r.status_code) print("Unable to transfer playback.") def spotRP(): accessToken = spotAuth() headers = {"Authorization": "Bearer "+accessToken} r = requests.get("https://api.spotify.com/v1/me/player/currently-playing", headers=headers) if r.status_code == 204: print("Nothing playing") quit() elif r.status_code != 200: print("Error: HTTP"+str(r.status_code)) quit() json = r.json() print("Remove \033[1m\033[95m"+json["item"]["name"]+"\033[0m from:") trackname = json["item"]["name"] trackuri = json["item"]["uri"] r = requests.get("https://api.spotify.com/v1/me", headers=headers) json = r.json() userid = json["id"] r = requests.get("https://api.spotify.com/v1/me/playlists?limit=50", headers=headers) json = r.json() j = 0 playdict = {} for i in json["items"]: if userid == i["owner"]["display_name"]: print("["+str(j)+"] "+i["name"]) playdict.update( {j: [i["name"], i["id"]]}) j += 1 elif i["collaborative"] == True: print("["+str(j)+"] "+i["name"]) playdict.update( {j: [i["name"], i["id"]]}) j += 1 choice = input("Select Playlist: ") try: choice = int(choice) except: quit() playlistid = playdict[choice][1] playlistname = playdict[choice][0] headers = {"Authorization": "Bearer "+accessToken, "Accept": "application/json", "Content-Type": "application/json"} payload = { "tracks": [{ "uri": trackuri }] } r = requests.delete("https://api.spotify.com/v1/playlists/"+playlistid+"/tracks", headers=headers, data=jsn.dumps(payload)) if r.status_code == 200: print("If \033[1m\033[95m"+trackname+"\033[0m was in \033[1m\033[96m"+playlistname+"\033[0m it has been removed.") else: print("Unable to remove song from specified playlist. Do you have access to do so?") return r.status_code def spotPL(): accessToken = spotAuth() headers = {"Authorization": "Bearer "+accessToken} print("Play:") r = requests.get("https://api.spotify.com/v1/me/playlists?limit=50", headers=headers) json = r.json() j = 0 playdict = {} for i in json["items"]: print("["+str(j)+"] "+i["name"]) playdict.update( {j: [i["name"], i["id"]]}) j += 1 choice = input("Select Playlist: ") try: choice = int(choice) except: quit() playlistid = playdict[choice][1] playlistname = playdict[choice][0] dev = spotDevice(headers, "playlist play") payload = {"context_uri": "spotify:playlist:"+playlistid} r = requests.put("https://api.spotify.com/v1/me/player/play?device_id="+dev["deviceid"], headers=headers, data=jsn.dumps(payload)) if r.status_code == 204: time.sleep(0.5) r = requests.get("https://api.spotify.com/v1/me/player/currently-playing", headers=headers) if r.status_code == 204: print("No active playback session") quit() elif r.status_code != 200: print("Error: HTTP"+str(r.status_code)) quit() json = r.json() trackname = json["item"]["name"] trackid = json["item"]["id"] print("Playing \033[1m\033[95m"+trackname+"\033[0m on \033[1m\033[92m"+dev["devicename"]+"\033[0m.") else: print("Unable to play \033[1m\033[95m"+trackname+"\033[0m.") return r.status_code def spotVL(vol): accessToken = spotAuth() headers = {"Authorization": "Bearer "+accessToken} dev = spotDevice(headers, "vol") r = requests.get("https://api.spotify.com/v1/me/player", headers=headers) print(r) json = r.json() curVol = json["device"]["volume_percent"] curVol = int(curVol) if vol == "up": vol = (curVol+10) if vol > 100: vol = 100 elif vol == "down": vol = (curVol-10) if vol < 0: vol = 0 r = requests.put("https://api.spotify.com/v1/me/player/volume?volume_percent="+str(vol), headers=headers) if r.status_code == 204: print("Volume on \033[1m\033[92m"+dev["devicename"]+"\033[0m set to "+str(vol)) else: json = r.json() reason = json["error"]["reason"] if reason == "VOLUME_CONTROL_DISALLOW": print("Device \033[1m\033[92m"+dev["devicename"]+"\033[0m does not allow volume to be controlled through API") else: print("No active playback devices") return r.status_code