CtrlK
BlogDocsLog inGet started
Tessl Logo

tessl/pypi-spotipy

A light weight Python library for the Spotify Web API

Overview
Eval results
Files

browse.mddocs/

Browse and Discover

Spotify's discovery and browse features including featured playlists, new releases, categories, personalized recommendations, and audio analysis capabilities. These endpoints provide access to Spotify's curated content and recommendation engine.

Capabilities

Featured Content

Access Spotify's editorially curated featured playlists and new releases.

def featured_playlists(self, country=None, locale=None, timestamp=None, limit=20, offset=0):
    """
    Get featured playlists.
    
    Args:
        country (str, optional): ISO 3166-1 alpha-2 country code
        locale (str, optional): Desired language for results (ISO 639-1 language code and ISO 3166-1 alpha-2 country code)
        timestamp (str, optional): ISO 8601 timestamp for when to retrieve featured playlists
        limit (int): Number of playlists to return (1-50, default: 20)
        offset (int): Index of first playlist (default: 0)
        
    Returns:
        dict: Object with message and paging object of featured playlists
    """

def new_releases(self, country=None, limit=20, offset=0):
    """
    Get new album releases.
    
    Args:
        country (str, optional): ISO 3166-1 alpha-2 country code
        limit (int): Number of albums to return (1-50, default: 20)
        offset (int): Index of first album (default: 0)
        
    Returns:
        dict: Paging object of new album releases
    """

Categories

Browse Spotify's genre and mood categories with associated playlists.

def categories(self, country=None, locale=None, limit=20, offset=0):
    """
    Get list of categories.
    
    Args:
        country (str, optional): ISO 3166-1 alpha-2 country code
        locale (str, optional): Desired language for results
        limit (int): Number of categories to return (1-50, default: 20)
        offset (int): Index of first category (default: 0)
        
    Returns:
        dict: Paging object of category objects
    """

def category(self, category_id, country=None, locale=None):
    """
    Get single category.
    
    Args:
        category_id (str): Spotify category ID
        country (str, optional): ISO 3166-1 alpha-2 country code
        locale (str, optional): Desired language for results
        
    Returns:
        dict: Category object with id, name, href, icons
    """

def category_playlists(self, category_id, country=None, limit=20, offset=0):
    """
    Get playlists for a category.
    
    Args:
        category_id (str): Spotify category ID
        country (str, optional): ISO 3166-1 alpha-2 country code
        limit (int): Number of playlists to return (1-50, default: 20)
        offset (int): Index of first playlist (default: 0)
        
    Returns:
        dict: Paging object of playlists for the category
    """

Recommendations

Get personalized track recommendations based on seed tracks, artists, and genres with fine-tuned audio features.

def recommendations(self, seed_artists=None, seed_genres=None, seed_tracks=None,
                   limit=20, country=None, **kwargs):
    """
    Get track recommendations.
    
    Args:
        seed_artists (list, optional): List of artist IDs for seed (max 5 total seeds)
        seed_genres (list, optional): List of genre names for seed (max 5 total seeds)
        seed_tracks (list, optional): List of track IDs for seed (max 5 total seeds)
        limit (int): Number of recommendations to return (1-100, default: 20)
        country (str, optional): ISO 3166-1 alpha-2 country code
        **kwargs: Audio feature targets and ranges (min_*, max_*, target_*)
        
    Audio Feature Parameters:
        - acousticness: 0.0-1.0
        - danceability: 0.0-1.0  
        - duration_ms: milliseconds
        - energy: 0.0-1.0
        - instrumentalness: 0.0-1.0
        - key: 0-11 (C, C#, D, etc.)
        - liveness: 0.0-1.0
        - loudness: -60.0 to 0.0 dB
        - mode: 0 (minor) or 1 (major)
        - popularity: 0-100
        - speechiness: 0.0-1.0
        - tempo: BPM
        - time_signature: 3-7
        - valence: 0.0-1.0 (positivity)
        
    Returns:
        dict: Recommendations object with tracks array and seed info
    """

def recommendation_genre_seeds(self):
    """
    Get available genre seeds for recommendations.
    
    Returns:
        dict: Object containing list of available genre strings
    """

Audio Analysis

Detailed audio analysis and features for tracks.

def audio_features(self, tracks=[]):
    """
    Get audio features for tracks.
    
    Args:
        tracks (list): List of track IDs or URIs (max 100)
        
    Returns:
        dict: Audio features objects with acousticness, danceability, energy, etc.
    """

def audio_analysis(self, track_id):
    """
    Get detailed audio analysis for a track.
    
    Args:
        track_id (str): Spotify track ID or URI
        
    Returns:
        dict: Detailed audio analysis with bars, beats, sections, segments, tatums, meta, track
    """

Usage Examples

Discovering Featured Content

import spotipy
from spotipy.oauth2 import SpotifyClientCredentials

sp = spotipy.Spotify(client_credentials_manager=SpotifyClientCredentials())

# Get featured playlists for US market
featured = sp.featured_playlists(country='US', limit=10)
print(f"Featured message: {featured['message']}")
print("\\nFeatured playlists:")

for playlist in featured['playlists']['items']:
    print(f"  📋 {playlist['name']} by {playlist['owner']['display_name']}")
    print(f"     {playlist['tracks']['total']} tracks, {playlist['followers']['total']} followers")
    print(f"     {playlist['description']}")

# Get new releases
new_releases = sp.new_releases(country='US', limit=10)
print("\\n🆕 New album releases:")

for album in new_releases['albums']['items']:
    artist_names = ', '.join([artist['name'] for artist in album['artists']])
    print(f"  💿 {album['name']} - {artist_names}")
    print(f"     Released: {album['release_date']} | Type: {album['album_type']}")
    if album['total_tracks'] > 1:
        print(f"     {album['total_tracks']} tracks")

Exploring Categories

# Get all categories
categories = sp.categories(country='US', limit=50)
print("🎭 Available categories:")

category_list = categories['categories']['items']
for category in category_list[:10]:  # Show first 10
    print(f"  {category['name']} (ID: {category['id']})")

# Explore specific category
pop_category = sp.category('pop', country='US')
print(f"\\n📂 Category: {pop_category['name']}")

# Get playlists for pop category
pop_playlists = sp.category_playlists('pop', country='US', limit=20)
print(f"\\nTop pop playlists:")

for playlist in pop_playlists['playlists']['items']:
    print(f"  🎵 {playlist['name']}")
    print(f"     {playlist['tracks']['total']} tracks, {playlist['followers']['total']} followers")

Personalized Recommendations

# Get available genres
genres = sp.recommendation_genre_seeds()
print(f"Available genres: {', '.join(genres['genres'][:10])}...")  # Show first 10

# Get recommendations based on favorite artists and genres
recommendations = sp.recommendations(
    seed_artists=['4Z8W4fKeB5YxbusRsdQVPb'],  # Radiohead
    seed_genres=['alternative', 'indie'],
    seed_tracks=['4iV5W9uYEdYUVa79Axb7Rh'],  # Mr. Brightside
    limit=20,
    country='US'
)

print("\\n🎯 Personalized recommendations:")
for track in recommendations['tracks']:
    artist_names = ', '.join([artist['name'] for artist in track['artists']])
    print(f"  🎵 {track['name']} - {artist_names}")
    print(f"     Popularity: {track['popularity']}/100")

# Show seed information
print("\\n🌱 Based on seeds:")
for seed in recommendations['seeds']:
    print(f"  {seed['type']}: {seed.get('id', 'N/A')} (after filtering: {seed['afterFilteringSize']})")

Advanced Recommendations with Audio Features

# Get upbeat, danceable recommendations
upbeat_recs = sp.recommendations(
    seed_genres=['pop', 'dance'],
    limit=15,
    target_danceability=0.8,    # High danceability
    target_energy=0.7,          # High energy
    target_valence=0.8,         # Positive mood
    min_tempo=120,              # At least 120 BPM
    max_tempo=140,              # Max 140 BPM
    target_popularity=70        # Reasonably popular
)

print("🕺 Upbeat, danceable recommendations:")
for track in upbeat_recs['tracks']:
    artist_names = ', '.join([artist['name'] for artist in track['artists']])
    print(f"  💃 {track['name']} - {artist_names}")

# Get chill, acoustic recommendations  
chill_recs = sp.recommendations(
    seed_genres=['acoustic', 'chill'],
    limit=10,
    target_acousticness=0.8,    # Highly acoustic
    target_energy=0.3,          # Low energy
    target_valence=0.6,         # Moderately positive
    max_loudness=-10,           # Not too loud
    target_instrumentalness=0.1 # Some vocals
)

print("\\n😌 Chill, acoustic recommendations:")
for track in chill_recs['tracks']:
    artist_names = ', '.join([artist['name'] for artist in track['artists']])
    print(f"  🎸 {track['name']} - {artist_names}")

Audio Features Analysis

# Analyze audio features of popular tracks
track_ids = [
    '4iV5W9uYEdYUVa79Axb7Rh',  # Mr. Brightside
    '0VjIjW4GlUAOLklx2J',      # Bohemian Rhapsody  
    '1301WleyT98MSxVHPZCA6M'   # Sweet Child O' Mine
]

# Get basic track info
tracks_info = sp.tracks(track_ids)
features = sp.audio_features(track_ids)

print("🎵 Audio Features Analysis:")
for track_info, feature in zip(tracks_info['tracks'], features):
    if feature:  # Check if features available
        print(f"\\n🎧 {track_info['name']} - {track_info['artists'][0]['name']}")
        print(f"   Key: {feature['key']} | Mode: {'Major' if feature['mode'] else 'Minor'}")
        print(f"   Tempo: {feature['tempo']:.1f} BPM | Time Signature: {feature['time_signature']}/4")
        print(f"   Energy: {feature['energy']:.2f} | Danceability: {feature['danceability']:.2f}")
        print(f"   Valence: {feature['valence']:.2f} | Acousticness: {feature['acousticness']:.2f}")
        print(f"   Loudness: {feature['loudness']:.1f} dB | Duration: {feature['duration_ms']/1000:.1f}s")

Detailed Audio Analysis

# Get detailed analysis for a track
track_id = '4iV5W9uYEdYUVa79Axb7Rh'  # Mr. Brightside
analysis = sp.audio_analysis(track_id)

print("🔬 Detailed Audio Analysis:")
print(f"Duration: {analysis['track']['duration']:.1f}s")
print(f"Key: {analysis['track']['key']} | Mode: {analysis['track']['mode']}")
print(f"Time Signature: {analysis['track']['time_signature']}")
print(f"Tempo: {analysis['track']['tempo']:.1f} BPM")

# Analyze sections
print(f"\\n📊 Song Structure:")
print(f"Bars: {len(analysis['bars'])}")
print(f"Beats: {len(analysis['beats'])}")  
print(f"Sections: {len(analysis['sections'])}")
print(f"Segments: {len(analysis['segments'])}")

# Show first few sections
print("\\n🎼 Sections breakdown:")
for i, section in enumerate(analysis['sections'][:5]):
    start_time = section['start']
    duration = section['duration']
    confidence = section['confidence']
    loudness = section['loudness']
    tempo = section['tempo']
    key = section['key']
    
    print(f"  Section {i+1}: {start_time:.1f}s-{start_time+duration:.1f}s")
    print(f"    Tempo: {tempo:.1f} BPM | Key: {key} | Loudness: {loudness:.1f} dB")
    print(f"    Confidence: {confidence:.2f}")

Discovery Workflow

def discover_music_by_mood(mood="happy", limit=15):
    """Discover music based on mood using audio features."""
    
    mood_profiles = {
        "happy": {
            "seed_genres": ["pop", "dance", "funk"],
            "target_valence": 0.8,
            "target_energy": 0.7,
            "target_danceability": 0.7,
            "min_tempo": 110
        },
        "sad": {
            "seed_genres": ["indie", "alternative", "singer-songwriter"],
            "target_valence": 0.3,
            "target_energy": 0.4,
            "target_acousticness": 0.6,
            "max_tempo": 100
        },
        "chill": {
            "seed_genres": ["chill", "ambient", "lo-fi"],
            "target_energy": 0.3,
            "target_acousticness": 0.7,
            "target_instrumentalness": 0.5,
            "max_loudness": -15
        },
        "workout": {
            "seed_genres": ["electro", "hip-hop", "rock"],
            "target_energy": 0.9,
            "target_danceability": 0.8,
            "min_tempo": 130,
            "max_tempo": 160
        }
    }
    
    if mood not in mood_profiles:
        print(f"Mood '{mood}' not available. Try: {', '.join(mood_profiles.keys())}")
        return
    
    profile = mood_profiles[mood]
    recommendations = sp.recommendations(limit=limit, **profile)
    
    print(f"🎭 {mood.title()} Music Recommendations:")
    for track in recommendations['tracks']:
        artist_names = ', '.join([artist['name'] for artist in track['artists']])
        print(f"  🎵 {track['name']} - {artist_names}")
        print(f"     Album: {track['album']['name']} | Popularity: {track['popularity']}/100")

# Discover music for different moods
discover_music_by_mood("happy", 10)
print()
discover_music_by_mood("chill", 8)

Market-Specific Discovery

def explore_market(country_code, limit=5):
    """Explore what's popular in a specific market."""
    
    print(f"🌍 Exploring {country_code} market:")
    
    # Featured playlists
    try:
        featured = sp.featured_playlists(country=country_code, limit=limit)
        print(f"\\n📋 Featured Playlists:")
        for playlist in featured['playlists']['items']:
            print(f"  {playlist['name']} ({playlist['tracks']['total']} tracks)")
    except Exception as e:
        print(f"  Featured playlists not available: {e}")
    
    # New releases
    try:
        releases = sp.new_releases(country=country_code, limit=limit)
        print(f"\\n💿 New Releases:")
        for album in releases['albums']['items']:
            artist_names = ', '.join([artist['name'] for artist in album['artists']])
            print(f"  {album['name']} - {artist_names}")
    except Exception as e:
        print(f"  New releases not available: {e}")
    
    # Categories
    try:
        categories = sp.categories(country=country_code, limit=limit)
        print(f"\\n🎭 Popular Categories:")
        for category in categories['categories']['items']:
            print(f"  {category['name']}")
    except Exception as e:
        print(f"  Categories not available: {e}")

# Explore different markets
markets = ['US', 'GB', 'DE', 'JP', 'BR']
for market in markets:
    explore_market(market, 3)
    print("-" * 50)

Audio Feature Ranges

When using recommendations with audio feature parameters:

  • acousticness: 0.0 (not acoustic) to 1.0 (very acoustic)
  • danceability: 0.0 (not danceable) to 1.0 (very danceable)
  • energy: 0.0 (low energy) to 1.0 (high energy)
  • instrumentalness: 0.0 (vocals) to 1.0 (instrumental)
  • liveness: 0.0 (studio) to 1.0 (live performance)
  • loudness: -60.0 to 0.0 dB (typical range: -60 to 0)
  • speechiness: 0.0 (not speech-like) to 1.0 (very speech-like)
  • valence: 0.0 (negative mood) to 1.0 (positive mood)
  • tempo: BPM (typical range: 50-200)
  • popularity: 0 (least popular) to 100 (most popular)
  • key: 0 (C) to 11 (B) in chromatic order
  • mode: 0 (minor) or 1 (major)
  • time_signature: 3 to 7 (beats per bar)

Use min_*, max_*, and target_* prefixes with these feature names for recommendation fine-tuning.

Install with Tessl CLI

npx tessl i tessl/pypi-spotipy

docs

authentication.md

browse.md

cache.md

client.md

index.md

playback.md

playlists.md

podcasts.md

user-library.md

tile.json