1 unstable release
Uses new Rust 2024
0.1.0 | May 28, 2025 |
---|
#262 in Audio
485KB
11K
SLoC
Spotify Web API
A wrapper for the Spotify Web API written in Rust.
Spotify Web API enables the creation of applications that can interact with Spotify's streaming service, such as retrieving content metadata, getting recommendations, creating and managing playlists, or controlling playback.
Adding as a Dependency
You can add this to your project by running the command
cargo add spotify_web_api
Examples
There are more examples in the examples folder.
Client Credentials
use spotify_web_api::{
api::{artists::GetArtist, Query as _},
model::Artist,
Spotify,
};
fn main() -> anyhow::Result<()> {
let spotify = Spotify::with_client_credentials("client_id", "client_secret")?;
spotify.request_token()?;
let artist: Artist = GetArtist::from("0559tR6WyukLWH68JIGBuC").query(&spotify)?;
println!("{artist:#?}");
Ok(())
}
Authorization Code with PKCE
use spotify_web_api::{
api::{users::GetCurrentUserProfile, AsyncQuery as _},
auth::scopes,
model::CurrentUserProfile,
AsyncSpotify,
};
use std::io::{self, Write};
#[tokio::main]
async fn main() -> anyhow::Result<()> {
let mut spotify = AsyncSpotify::with_authorization_code_pkce(
"client_id",
"http://127.0.0.1:8888/callback",
scopes::all(),
)?;
let user_auth_url = spotify.user_authorization_url();
println!("User Authorization URL:\n\n{user_auth_url}");
println!("Please paste the full URL you were redirected to after authorization:\n");
io::stdout().flush()?;
let mut redirect_url = String::new();
io::stdin().read_line(&mut redirect_url)?;
let redirect_url = redirect_url.trim();
spotify.request_token_from_redirect_url(redirect_url).await?;
let user_profile: CurrentUserProfile = GetCurrentUserProfile.query_async(&spotify).await?;
println!("{user_profile:#?}");
Ok(())
}
Which OAuth flow should I use? (source)
Choosing one flow over the rest depends on the application you are building:
- In scenarios where storing the client secret is not safe (e.g. desktop, mobile apps or JavaScript web apps running in the browser), you can use the authorization code with PKCE, as it provides protection against attacks where the authorization code may be intercepted.
- For some applications running on the backend, such as CLIs or daemons, the system authenticates and authorizes the app rather than a user. For these scenarios, Client credentials is the typical choice. This flow does not include user authorization, so only endpoints that do not request user information (e.g. user profile data) can be accessed.
The following table summarizes the flows' behaviors:
Flow | Access User Resources | Requires Secret Key (Server-Side) | Access Token Refresh |
---|---|---|---|
Authorization code with PKCE | Yes | No | Yes |
Client credentials | No | Yes | No |
API
Supported endpoints are organized under the api
module. To interact with an endpoint, you can use either the Query
or AsyncQuery
traits.
Query
is designed for blocking code, making it ideal for synchronous workflows or environments where asynchronous execution is unnecessary or not supported. Opt for this when simplicity is key, such as in single-threaded environments or scripts where blocking is acceptable.AsyncQuery
is intended for asynchronous code and integrates seamlessly with an asynchronous runtime of your choice, such asTokio
orasync-std
. This approach is particularly useful when working in environments that benefit from non-blocking operations. Use this trait when building applications that require high concurrency or when interacting with other asynchronous code.
There are additional helpers to handle different cases:
api::ignore
: Ignore the Spotify response (useful for POST or PUT endpoints).api::paged
: Fetch results that are paginated.api::raw
: Return the raw data from Spotify instead of deserializing into a structure.
You're not restricted to the predefined endpoints; you can define your own by implementing the Endpoint
trait. See example.
All endpoints return data types chosen by the caller, provided these types implement serde
's Deserialize
trait. The library offers predefined structs in the model
module, but you are free to use your own structs by implementing the Deserialize
trait. This flexibility is particularly useful when a custom data structure better suits the your needs or when avoiding the overhead of deserializing the entire response is desirable. See example.
Feature Flags
A set of feature flags are available to customize the data models. These are enabled by default, but you can disable them to reduce the size of the compiled library or to avoid unnecessary data in your application.
markets
- Enables theavailable_markets
field in various models, such asTrack
. This field contains a list of markets where the content is available.page_items
- Enables the field in various models that contain paginated items, such as thetracks
field inPlaylist
.
Implemented Endpoints
Format: [x]
[Title]
[Method]
[Endpoint]
[Spotify Docs]
Albums
- Get Album
GET
/albums/{id}
get-an-album - Get Several Albums
GET
/albums
get-multiple-albums - Get Album Tracks
GET
/albums/{id}/tracks
get-an-albums-tracks - Get User's Saved Albums
GET
me/albums
get-users-saved-albums - Save Albums for Current User
PUT
me/albums
save-albums-user - Remove User's Saved Albums
DELETE
me/albums
remove-albums-user - Check User's Saved Albums
GET
me/albums/contains
check-users-saved-albums - Get New Releases
GET
/browse/new-releases
get-new-releases
Artists
- Get Artist
GET
/artists/{id}
get-an-artist - Get Several Artists
GET
/artists
get-multiple-artists - Get Artist's Albums
GET
/artists/{id}/albums
get-an-artists-albums - Get Artist's Top Tracks
GET
/artists/{id}/top-tracks
get-an-artists-top-tracks
Audiobooks
- Get an Audiobook
GET
/audiobooks/{id}
get-an-audiobook - Get Several Audiobooks
GET
/audiobooks
get-multiple-audiobooks - Get Audiobook Chapters
GET
/audiobooks/{id}/chapters
get-audiobook-chapters - Get User's Saved Audiobooks
GET
me/audiobooks
get-users-saved-audiobooks - Save Audiobooks for Current User
PUT
me/audiobooks
save-audiobooks-user - Remove User's Saved Audiobooks
DELETE
me/audiobooks
remove-audiobooks-user - Check User's Saved Audiobooks
GET
me/audiobooks/contains
check-users-saved-audiobooks
Categories
- Get Several Browse Categories
GET
/browse/categories
get-categories - Get Single Browse Category
GET
/browse/categories/{category_id}
get-a-category
Chapters
- Get a Chapter
GET
/chapters/{id}
get-a-chapter - Get Several Chapters
GET
/chapters
get-several-chapters
Episodes
- Get Episode
GET
/episodes/{id}
get-an-episode - Get Several Episodes
GET
/episodes
get-multiple-episodes - Get User's Saved Episodes
GET
me/episodes
get-users-saved-episodes - Save Episodes for Current User
PUT
me/episodes
save-episodes-user - Remove User's Saved Episodes
DELETE
me/episodes
remove-episodes-user - Check User's Saved Episodes
GET
me/episodes/contains
check-users-saved-episodes
Genres
- Get Available Genre Seeds
GET
/recommendations/available-genre-seeds
get-recommendation-genres
Markets
- Get Available Markets
GET
/markets
get-available-markets
Player
- Get Playback State
GET
/me/player
get-information-about-the-users-current-playback - Transfer Playback
PUT
/me/player
transfer-a-users-playback - Get Available Devices
GET
/me/player/devices
get-a-users-available-devices - Get Currently Playing Track
GET
/me/player/currently-playing
get-the-users-currently-playing-track - Start/Resume Playback
PUT
/me/player/play
start-a-users-playback - Pause Playback
PUT
/me/player/pause
pause-a-users-playback - Skip To Next
POST
/me/player/next
skip-users-playback-to-next-track - Skip To Previous
POST
/me/player/previous
skip-users-playback-to-previous-track - Seek To Position
PUT
/me/player/seek
seek-to-position-in-currently-playing-track - Set Repeat Mode
PUT
/me/player/repeat
set-repeat-mode-on-users-playback - Set Playback Volume
PUT
/me/player/volume
set-volume-for-users-playback - Toggle Playback Shuffle
PUT
/me/player/shuffle
toggle-shuffle-for-users-playback - Get Recently Played Tracks
GET
/me/player/recently-played
get-recently-played - Get the User's Queue
GET
/me/player/queue
get-queue - Add Item to Playback Queue
POST
/me/player/queue
add-to-queue
Playlists
- Get Playlist
GET
/playlists/{playlist_id}
get-playlist - Change Playlist Details
PUT
/playlists/{playlist_id}
change-playlist-details - Get Playlist Items
GET
/playlists/{playlist_id}/tracks
get-playlists-tracks - Update Playlist Items
PUT
/playlists/{playlist_id}/tracks
reorder-or-replace-playlists-tracks - Add Items to Playlist
POST
/playlists/{playlist_id}/tracks
add-tracks-to-playlist - Remove Playlist Items
DELETE
/playlists/{playlist_id}/tracks
remove-tracks-playlist - Get Current User's Playlists
GET
/me/playlists
get-a-list-of-current-users-playlists - Get User's Playlists
GET
/users/{user_id}/playlists
get-list-users-playlists - Create Playlist
POST
/users/{user_id}/playlists
create-playlist - Get Playlist Cover Image
GET
/playlists/{playlist_id}/images
get-playlist-cover - Add Custom Playlist Cover Image
PUT
/playlists/{playlist_id}/images
upload-custom-playlist-cover
Search
- Search for Item
GET
/search
search
Shows
- Get Show
GET
/shows/{id}
get-a-show - Get Several Shows
GET
/shows
get-multiple-shows - Get Show Episodes
GET
/shows/{id}/episodes
get-a-shows-episodes - Get User's Saved Shows
GET
me/shows
get-users-saved-shows - Save Shows for Current User
PUT
me/shows
save-shows-user - Remove User's Saved Shows
DELETE
me/shows
remove-shows-user - Check User's Saved Shows
GET
me/shows/contains
check-users-saved-shows
Tracks
- Get Track
GET
/tracks/{id}
get-track - Get Several Tracks
GET
/tracks
get-several-tracks - Get User's Saved Tracks
GET
me/tracks
get-users-saved-tracks - Save Tracks for Current User
PUT
me/tracks
save-tracks-user - Remove User's Saved Tracks
DELETE
me/tracks
remove-tracks-user - Check User's Saved Tracks
GET
me/tracks/contains
check-users-saved-tracks
Users
- Get Current User's Profile
GET
/me
get-current-users-profile - Get User's Top Items
GET
/me/top/{type}
get-users-top-artists-and-tracks - Get User's Profile
GET
/users/{user_id}
get-users-profile - Follow Playlist
PUT
/playlists/{playlist_id}/followers
follow-playlist - Unfollow Playlist
DELETE
/playlists/{playlist_id}/followers
unfollow-playlist - Get Followed Artists
GET
/me/following
get-followed - Follow Artists or Users
PUT
/me/following
follow-artists-users - Unfollow Artists or Users
DELETE
/me/following
unfollow-artists-users - Check If User Follows Artists or Users
GET
/me/following/contains
check-current-user-follows - Check if Current User Follows Playlist
GET
/playlists/{playlist_id}/followers/contains
check-if-user-follows-playlist
License
Licensed under either of Apache License, Version 2.0 or MIT license at your option.Dependencies
~7–19MB
~265K SLoC