Files
spotvinyl/final-loop/src/get_uri.py
2025-12-06 13:21:03 +01:00

138 lines
4.3 KiB
Python

from typing import Tuple
import requests
import spotipy
from spotipy.oauth2 import SpotifyOAuth
import sys
from urllib.parse import urlencode
from urllib.parse import urlencode, urlparse, parse_qs
import webbrowser
import time
import base64
CLIENT_ID = 'a1b29f64bef643b5ade0944830637510'
CLIENT_SECRET = '1d74196e6fec41f9986917afd57df3da'
REDIRECT_URI = 'https://vinyly.couraud.xyz'
SCOPE = 'user-modify-playback-state user-read-playback-state'
TOKEN_FILE = 'spotify_token.json'
import json
def get_spotify_token():
# Try to load existing token
try:
with open(TOKEN_FILE) as f:
data = json.load(f)
if data['expires_at'] > time.time():
return data['access_token']
# refresh token
resp = requests.post(
'https://accounts.spotify.com/api/token',
data={'grant_type': 'refresh_token', 'refresh_token': data['refresh_token']},
headers={'Authorization': 'Basic ' + base64.b64encode(f"{CLIENT_ID}:{CLIENT_SECRET}".encode()).decode()}
).json()
data['access_token'] = resp['access_token']
data['expires_at'] = time.time() + resp['expires_in']
with open(TOKEN_FILE, 'w') as f2:
json.dump(data, f2)
return data['access_token']
except FileNotFoundError:
# Get authorization code
auth_url = 'https://accounts.spotify.com/authorize?' + urlencode({
'client_id': CLIENT_ID,
'response_type': 'code',
'redirect_uri': REDIRECT_URI,
'scope': SCOPE
})
print("Open this URL and authorize:", auth_url)
webbrowser.open(auth_url)
code = input("Paste the full redirected URL here: ")
code = parse_qs(urlparse(code).query)['code'][0]
# Exchange code for tokens
resp = requests.post(
'https://accounts.spotify.com/api/token',
data={
'grant_type': 'authorization_code',
'code': code,
'redirect_uri': REDIRECT_URI
},
headers={'Authorization': 'Basic ' + base64.b64encode(f"{CLIENT_ID}:{CLIENT_SECRET}".encode()).decode()}
).json()
data = {
'access_token': resp['access_token'],
'refresh_token': resp['refresh_token'],
'expires_at': time.time() + resp['expires_in']
}
with open(TOKEN_FILE, 'w') as f:
json.dump(data, f)
return data['access_token']
HEADERS_LUT = {
"X-Client-Id": "58bd3c95768941ea9eb4350aaa033eb3",
"Accept-Encoding": "gzip, deflate",
"Connection": "close",
"App-Platform": "iOS",
"Accept": "*/*",
"User-Agent": "Spotify/8.5.68 iOS/13.4 (iPhone9,3)",
"Accept-Language": "en",
"Spotify-App-Version": "8.5.68",
}
MEDIA_REF_LUT_URL = "https://spclient.wg.spotify.com:443/scannable-id/id"
auth_url = "https://accounts.spotify.com/authorize?" + urlencode({
"client_id": CLIENT_ID,
"response_type": "code",
"redirect_uri": REDIRECT_URI,
"scope": SCOPE
})
def get_uri(media_ref: int):
with open("/app/songs.json") as f:
code_to_url = json.load(f)
uri = code_to_url.get(str(media_ref))
if uri:
return uri
else:
return -1
def get_info(uri: str, token: str) -> Tuple[dict, dict]:
"""Query the Spotify API to get information about a URI."""
info_headers = {
"Content-Type": "application/json",
"Accept": "application/json",
"Authorization": f"Bearer {token}"
}
split = uri.split(":")
content_type = split[-2] + "s"
id = split[-1]
response = requests.get(f"https://api.spotify.com/v1/{content_type}/{id}", headers=info_headers)
response.raise_for_status()
resp = response.json()
result = {
"name": resp["name"],
"type": split[-2],
"url": resp["external_urls"]["spotify"],
}
if "artists" in resp:
result['artists'] = []
for a in resp['artists']:
result["artists"].append(a["name"])
if "album" in resp:
result['album'] = resp['album']['name']
if "description" in resp:
result["description"] = resp['description']
return result, resp