Created
November 1, 2021 01:20
-
-
Save dangrous/f718d23c76b829ca0be212dffe6f801d to your computer and use it in GitHub Desktop.
Python script to pull data from Spotify
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import requests | |
import json | |
import csv | |
from random import randint | |
from datetime import datetime | |
from requests.auth import HTTPBasicAuth | |
client_id = "XXXXXXXX" # This is real in the real one | |
client_secret = "XXXXXXXX" # This is real in the real one | |
with open("spotifytoken.txt", 'r') as f: | |
token = f.read() | |
def test_token(): | |
global token | |
test = requests.get("https://api.spotify.com/v1/artists/0TnOYISbd1XYRBk9myaseg", | |
headers={ | |
"Accept": "application/json", | |
"Content-Type": "application/json", | |
"Authorization": "Bearer " + token | |
} | |
) | |
if test.status_code == 401: | |
print("The token is invalid. Obtaining a new one...") | |
response = requests.post("https://accounts.spotify.com/api/token", | |
auth=HTTPBasicAuth(client_id,client_secret), | |
data={"grant_type": "client_credentials"} | |
).json() | |
with open("spotifytoken.txt", "w+") as f: | |
f.write(response['access_token']) | |
f.seek(0) | |
token = f.read() | |
test_token() | |
if "error" in test: | |
print("Sorry, there's been an error. Trying once more...") | |
test_token() | |
def find_popularity(search_term): | |
search_term_url = search_term.replace(" ", "%20") | |
search = requests.get("https://api.spotify.com/v1/search?q="+search_term_url+"&type=artist&limit=10", | |
headers={ | |
"Accept": "application/json", | |
"Content-Type": "application/json", | |
"Authorization": "Bearer " + token | |
} | |
).json() | |
found = False | |
multiple = False | |
if "error" in search: | |
print(search) | |
else: | |
for item in search['artists']['items']: | |
if item['name'].casefold() == search_term.casefold(): | |
print(item['name']," - Popularity: ",item['popularity']) | |
if found and not multiple: | |
multiple = True | |
found = True | |
if multiple: | |
print("Uh oh, there's more than one artist by that name!") | |
if not found: | |
print("Sorry, we couldn't find an exact match.") | |
again = input("Want to search again? Do it here, or type 'q' to quit.: ") | |
if again == 'q': | |
return | |
find_popularity(again) | |
def csv_madness(): | |
with open('data.csv', mode='r') as csv_file: | |
reader = csv.reader(csv_file) | |
columns = [] | |
data = {} | |
headers = True | |
for row in reader: | |
if headers: | |
for header in row: | |
columns.append(header) | |
headers = False | |
else: | |
data[row[0]] = {} | |
length = len(row) | |
for x in range(0,length): | |
data[row[0]][columns[x]] = row[x] | |
today = datetime.now().strftime("%m/%d/%Y %H:%M:%S") | |
if columns[-1][:10] == today[:10]: | |
response = input("You've already pulled data for today. Do you want to (c)ontinue or (q)uit? ") | |
if response == "q": | |
return | |
data = add_fifty_top_track_artists_to_dict(data, columns) | |
data = add_random_artists_to_dict(data, columns, 5) | |
columns.append(today) | |
all_artists = [] | |
for artist in data: | |
all_artists.append(data[artist]['id']) | |
while len(all_artists) > 0: | |
artists = requests.get("https://api.spotify.com/v1/artists?ids=" + ','.join(all_artists[0:50]), | |
headers={ | |
"Accept": "application/json", | |
"Content-Type": "application/json", | |
"Authorization": "Bearer " + token | |
} | |
).json() | |
if "error" in artists: | |
print(artists) | |
else: | |
for artist in artists['artists']: | |
data[artist['id']][today] = artist['popularity'] | |
all_artists = all_artists[50:] | |
with open('data.csv', mode='w') as csv_file: | |
writer = csv.DictWriter(csv_file, fieldnames=columns) | |
writer.writeheader() | |
for artist in data: | |
newversion = {} | |
for key, value in data[artist].items(): | |
newversion[key] = value | |
writer.writerow(newversion) | |
def add_fifty_top_track_artists_to_dict(dict, columns): | |
playlist = requests.get("https://api.spotify.com/v1/playlists/37i9dQZEVXbMDoHDwVN2tF", | |
headers={ | |
"Accept": "application/json", | |
"Content-Type": "application/json", | |
"Authorization": "Bearer " + token | |
} | |
).json() | |
if "error" in playlist: | |
print(playlist) | |
else: | |
for track in playlist['tracks']['items']: | |
for artist in track['track']['album']['artists']: | |
if artist['id'] not in dict: | |
dict[artist['id']] = {} | |
dict[artist['id']]['id'] = artist['id'] | |
dict[artist['id']]['name'] = artist['name'] | |
for column in columns[2:]: | |
dict[artist['id']][column] = "n/a" | |
return dict | |
# For whatever reason Spotify is only giving me the top 2000 in the US but that's okay still. | |
def add_random_artists_to_dict(dict, columns, number): | |
for _ in range(0,number): | |
search = requests.get(f"https://api.spotify.com/v1/search?q=year:0000-9999&type=artist&limit=1&offset={randint(0,1999)}", | |
headers={ | |
"Accept": "application/json", | |
"Content-Type": "application/json", | |
"Authorization": "Bearer " + token | |
} | |
).json() | |
if "error" in search: | |
print(search) | |
else: | |
for artist in search['artists']['items']: | |
if artist['id'] not in dict: | |
dict[artist['id']] = {} | |
dict[artist['id']]['id'] = artist['id'] | |
dict[artist['id']]['name'] = artist['name'] | |
for column in columns[2:]: | |
dict[artist['id']][column] = "n/a" | |
return dict | |
test_token() | |
csv_madness() | |
# find_popularity(input("What artist are you looking for? ")) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment