added threading for the lyrics download for speed

added update print to console if updated
This commit is contained in:
Brandon4466
2023-02-10 22:57:12 -08:00
parent dcd2fc068f
commit c18594855e
27 changed files with 2245 additions and 25 deletions

0
canvas/src/__init__.py Normal file
View File

63
canvas/src/app.py Normal file
View File

@@ -0,0 +1,63 @@
from fastapi import FastAPI
from fastapi.middleware.cors import CORSMiddleware
import os
import asyncio
import canvas
from constants import TOKEN_RENEW_TIME
API_HOST = "https://gew1-spclient.spotify.com"
CANVAS_ROUTE = "/canvaz-cache/v0/canvases"
TOKEN_ENDPOINT = "https://open.spotify.com/get_access_token?reason=transport"
TOKEN_RENEW_TIME = 900
TRACK_URI_PREFIX = "spotify:track:"
OAUTH_SCOPES = "playlist-read"
app = FastAPI()
ORIGIN = os.getenv('HOST_ORIGIN')
origins = [
ORIGIN,
"http://localhost:3000",
]
app.add_middleware(
CORSMiddleware,
allow_origins=origins,
allow_credentials=True,
allow_methods=["*"],
allow_headers=["*"],
)
access_token = ""
@app.get('/api/canvas/{track_id}')
def get_track_canvas(track_id):
try:
canvas_url = canvas.get_canvas_for_track(access_token, track_id)
return {'success': 'true', 'canvas_url': canvas_url}
except AttributeError:
return {'success': 'false', 'message': 'No canvas found for this track'}
except ConnectionError:
return {'success': 'false', 'message': 'failed to connect to Spotify'}
@app.get('/api/health')
def health():
return "up"
async def refresh_token():
global access_token
while True:
print('INFO: Getting a fresh Spotify access token')
try:
access_token = canvas.get_access_token()
except Exception as e:
print('ERROR: Failed to get a new access token: %s' % e)
await asyncio.sleep(TOKEN_RENEW_TIME)
@app.on_event("startup")
async def startup_event():
asyncio.get_event_loop().create_task(refresh_token())

47
canvas/src/canvas.py Normal file
View File

@@ -0,0 +1,47 @@
import requests
import random
from protos.canvas_pb2 import EntityCanvazRequest, EntityCanvazResponse
API_HOST = "https://gew1-spclient.spotify.com"
CANVAS_ROUTE = "/canvaz-cache/v0/canvases"
TOKEN_ENDPOINT = "https://open.spotify.com/get_access_token?reason=transport"
TOKEN_RENEW_TIME = 900
TRACK_URI_PREFIX = "spotify:track:"
OAUTH_SCOPES = "playlist-read"
def get_access_token():
try:
response = requests.get(TOKEN_ENDPOINT)
data = response.json()
return data["accessToken"]
except Exception as e:
raise Exception(e)
def get_canvas_for_track(access_token, track_id):
canvas_request = EntityCanvazRequest()
canvas_request_entities = canvas_request.entities.add()
canvas_request_entities.entity_uri = TRACK_URI_PREFIX + track_id
try:
resp = requests.post(
API_HOST + CANVAS_ROUTE,
headers={
"Content-Type": "application/x-protobuf",
"Authorization": "Bearer %s" % access_token
},
data=canvas_request.SerializeToString(),
)
except:
raise ConnectionError
canvas_response = EntityCanvazResponse()
canvas_response.ParseFromString(resp.content)
if(len(canvas_response.canvases) == 0):
raise AttributeError
canvas = random.choice(canvas_response.canvases)
return canvas.url

7
canvas/src/constants.py Normal file
View File

@@ -0,0 +1,7 @@
API_HOST = "https://gew1-spclient.spotify.com"
CANVAS_ROUTE = "/canvaz-cache/v0/canvases"
TOKEN_ENDPOINT = "https://open.spotify.com/get_access_token?reason=transport"
TOKEN_RENEW_TIME = 900
TRACK_URI_PREFIX = "spotify:track:"
OAUTH_SCOPES = "playlist-read"

View File

@@ -0,0 +1,36 @@
# -*- coding: utf-8 -*-
# Generated by the protocol buffer compiler. DO NOT EDIT!
# source: protos/canvas.proto
"""Generated protocol buffer code."""
from google.protobuf.internal import builder as _builder
from google.protobuf import descriptor as _descriptor
from google.protobuf import descriptor_pool as _descriptor_pool
from google.protobuf import symbol_database as _symbol_database
# @@protoc_insertion_point(imports)
_sym_db = _symbol_database.Default()
DESCRIPTOR = _descriptor_pool.Default().AddSerializedFile(b'\n\x13protos/canvas.proto\x12\x17\x63om.spotify.canvazcache\"3\n\x06\x41rtist\x12\x0b\n\x03uri\x18\x01 \x01(\t\x12\x0c\n\x04name\x18\x02 \x01(\t\x12\x0e\n\x06\x61vatar\x18\x03 \x01(\t\"\xe6\x02\n\x14\x45ntityCanvazResponse\x12\x46\n\x08\x63\x61nvases\x18\x01 \x03(\x0b\x32\x34.com.spotify.canvazcache.EntityCanvazResponse.Canvaz\x12\x16\n\x0ettl_in_seconds\x18\x02 \x01(\x03\x1a\xed\x01\n\x06\x43\x61nvaz\x12\n\n\x02id\x18\x01 \x01(\t\x12\x0b\n\x03url\x18\x02 \x01(\t\x12\x0f\n\x07\x66ile_id\x18\x03 \x01(\t\x12+\n\x04type\x18\x04 \x01(\x0e\x32\x1d.com.spotify.canvazcache.Type\x12\x12\n\nentity_uri\x18\x05 \x01(\t\x12/\n\x06\x61rtist\x18\x06 \x01(\x0b\x32\x1f.com.spotify.canvazcache.Artist\x12\x10\n\x08\x65xplicit\x18\x07 \x01(\x08\x12\x13\n\x0buploaded_by\x18\x08 \x01(\t\x12\x0c\n\x04\x65tag\x18\t \x01(\t\x12\x12\n\ncanvas_uri\x18\x0b \x01(\t\"\x88\x01\n\x13\x45ntityCanvazRequest\x12\x45\n\x08\x65ntities\x18\x01 \x03(\x0b\x32\x33.com.spotify.canvazcache.EntityCanvazRequest.Entity\x1a*\n\x06\x45ntity\x12\x12\n\nentity_uri\x18\x01 \x01(\t\x12\x0c\n\x04\x65tag\x18\x02 \x01(\t*R\n\x04Type\x12\t\n\x05IMAGE\x10\x00\x12\t\n\x05VIDEO\x10\x01\x12\x11\n\rVIDEO_LOOPING\x10\x02\x12\x18\n\x14VIDEO_LOOPING_RANDOM\x10\x03\x12\x07\n\x03GIF\x10\x04\x42\x16\n\x12\x63om.spotify.canvazH\x02\x62\x06proto3')
_builder.BuildMessageAndEnumDescriptors(DESCRIPTOR, globals())
_builder.BuildTopDescriptorsAndMessages(DESCRIPTOR, 'protos.canvas_pb2', globals())
if _descriptor._USE_C_DESCRIPTORS == False:
DESCRIPTOR._options = None
DESCRIPTOR._serialized_options = b'\n\022com.spotify.canvazH\002'
_TYPE._serialized_start=601
_TYPE._serialized_end=683
_ARTIST._serialized_start=48
_ARTIST._serialized_end=99
_ENTITYCANVAZRESPONSE._serialized_start=102
_ENTITYCANVAZRESPONSE._serialized_end=460
_ENTITYCANVAZRESPONSE_CANVAZ._serialized_start=223
_ENTITYCANVAZRESPONSE_CANVAZ._serialized_end=460
_ENTITYCANVAZREQUEST._serialized_start=463
_ENTITYCANVAZREQUEST._serialized_end=599
_ENTITYCANVAZREQUEST_ENTITY._serialized_start=557
_ENTITYCANVAZREQUEST_ENTITY._serialized_end=599
# @@protoc_insertion_point(module_scope)