SongBPM API: Get song tempo and key
Finds the best SongBPM match for a song title and artist and returns its tempo, musical key, Camelot key, length and time signature.
Unofficial. Not affiliated with or endorsed by SongBPM.
Inputs
Values from the run on Oct 23, 2026, shown under Output.
- Song, required
song Song title, for example Blinding Lights.
Blinding Lights
- Artist, required
artist Performing artist, for example The Weeknd.
The Weeknd
Input as JSON
{ "song": "Blinding Lights", "artist": "The Weeknd"}Output
{ "song": "Blinding Lights", "album": null, "artist": "The Weeknd", "energy": null, "length": "3:20", "tempo_bpm": 171, "camelot_key": "3B", "musical_key": "C♯/D♭ major" , "acousticness": null, "danceability": null, "songbpm_link": "https://songbpm.com/@the-weeknd/blinding-lights-c8d0a298-1020-47aa-a9a2-99bcf096cb84" , "length_seconds": 200, "time_signature": "4/4" }Code
curl https://api.fous.com/v1/runs \ -H "Authorization: Bearer $FOUS_API_KEY" \ -H "Content-Type: application/json" \ -d '{"method":"songbpm.com/get_song_tempo_and_key","input":{"song":"Blinding Lights","artist":"The Weeknd"}}' # Save as fous.py, then run: python3 fous.pyimport json, os, timefrom urllib.error import HTTPErrorfrom urllib.request import Request, urlopenAPI = "https://api.fous.com/v1/runs" KEY = os.environ["FOUS_API_KEY"]HEADERS = { "Authorization": f"Bearer {KEY}", "Content-Type": "application/json" ,}def call(url, body=None): data = json.dumps(body).encode() if body else None request = Request(url, data, HEADERS) try: with urlopen(request, timeout=120) as r: return r.status, json.load(r) except HTTPError as error: message = json.load(error)["error"]["message"] raise RuntimeError(message) from errorstatus, run = call(API, { "method": "songbpm.com/get_song_tempo_and_key" , "input": { "song": "Blinding Lights", "artist": "The Weeknd" }})# 202: still going after 30 s. Ask again until it ends.while status == 202: time.sleep(2) status, run = call(f"{API}/{run['id']}")print(json.dumps(run["data"], indent=2))// Save as fous.mjs, then run: node fous.mjsconst api = "https://api.fous.com/v1/runs" ;const headers = { Authorization: `Bearer ${process.env.FOUS_API_KEY}`, "Content-Type": "application/json" ,};let response = await fetch(api, { method: "POST", headers, body: JSON.stringify({ "method": "songbpm.com/get_song_tempo_and_key" , "input": { "song": "Blinding Lights", "artist": "The Weeknd" } }), signal: AbortSignal.timeout(120_000),});let run = await response.json();// 202: still going after 30 s. Ask again until it ends.while (response.status === 202) { await new Promise((done) => setTimeout(done, 2_000)); response = await fetch(`${api}/${run.id}`, { headers }); run = await response.json();}if (!response.ok) throw new Error(run.error.message);console.log(run.data);# Connect your agent to Fous once, over MCP (Streamable HTTP):# https://api.fous.com/mcp# Set FOUS_API_KEY first: create a key at https://app.fous.com/keys.# Claude Codeclaude mcp add \ --scope user \ --transport http fous https://api.fous.com/mcp \ --header "Authorization: Bearer ${FOUS_API_KEY:?Set FOUS_API_KEY to your Fous API key}"# Codexcodex mcp add fous \ --url https://api.fous.com/mcp \ --bearer-token-env-var FOUS_API_KEY# Cursor, VS Code, Windsurf, Cline and morenpx -y add-mcp https://api.fous.com/mcp -g -n fous \ --header "Authorization: Bearer ${FOUS_API_KEY:?Set FOUS_API_KEY to your Fous API key}"# Then ask your agent:# "Use Fous to run songbpm.com/get_song_tempo_and_key# with {"song":"Blinding Lights","artist":"The Weeknd"}"Over HTTP, the answer’s data holds the output. A run still going after 30 seconds answers 202 with its id: ask GET /v1/runs/{id} until it ends.
Schema
Input schema
{ "type": "object", "required": [ "song", "artist" ], "properties": { "song": { "type": "string", "description": "Song title, for example Blinding Lights." }, "artist": { "type": "string", "description": "Performing artist, for example The Weeknd." } }, "additionalProperties": false}Output schema
{ "type": "object", "required": [ "song", "artist", "album", "tempo_bpm", "musical_key", "camelot_key", "length", "length_seconds", "time_signature", "danceability", "energy", "acousticness", "songbpm_link" ], "properties": { "song": { "type": "string", "description": "Matched song title." }, "album": { "type": [ "string", "null" ], "description": "Album name, when available." }, "artist": { "type": "string", "description": "Matched artist." }, "energy": { "type": [ "number", "null" ], "description": "Energy on a 0–100 scale when shown." }, "length": { "type": [ "string", "null" ], "description": "Song length, such as 3:20." }, "tempo_bpm": { "type": "number", "description": "Tempo in beats per minute." }, "camelot_key": { "type": [ "string", "null" ], "description": "Camelot mixing key derived from musical key and mode." }, "musical_key": { "type": [ "string", "null" ], "description": "Musical key and mode, when shown." }, "acousticness": { "type": [ "number", "null" ], "description": "Acousticness on a 0–100 scale when shown." }, "danceability": { "type": [ "number", "null" ], "description": "Danceability on a 0–100 scale when shown." }, "songbpm_link": { "type": "string", "description": "Link to the matched SongBPM song page." }, "length_seconds": { "type": [ "integer", "null" ], "description": "Song length in seconds.", "x-fous-developer": true }, "time_signature": { "type": [ "string", "null" ], "description": "Beats per bar as a time signature when shown." } }, "additionalProperties": false}- Price
- 1 credit per completed run (1¢ with pay as you go); failed runs are free.
- Method
songbpm.com/get_song_tempo_and_key- Returns
- song, artist, tempo_bpm, musical_key, camelot_key, length, time_signature, songbpm_link
Use it from your agent
Give your agent this line. It reads SKILL.md, gets a Fous API key and connects the Fous MCP server. Its run then takes the method songbpm.com/get_song_tempo_and_key with the inputs above.
Ask your agent
- What is the tempo in BPM and musical key of Blinding Lights by The Weeknd?
- I'm DJing tonight and need the Camelot key for Levitating by Dua Lipa, can you check songbpm.com?
- How long is Shape of You by Ed Sheeran and what time signature is it in?
- Look up the BPM and key for Bad Guy by Billie Eilish so I can match it with my playlist.
- Find the tempo, key, and length of Watermelon Sugar by Harry Styles.
See more
Gets a Deezer song's tempo, ISRC, loudness gain and recording details from its title, track link or track ID. An artist name helps pick the right recording.
deezer.com/get_song_detailsFinds the best-matching studio recording on MusicBrainz for a song title and artist. Returns its ISRCs, first release date and up to 25 of its earliest releases.
musicbrainz.org/get_song_identifiersFinds a Spotify song by title (optionally narrowed by artist), track link, URI or track ID and returns its public play count and details. Without an artist, the most-played exact title match wins. Previews and ISRC may be unavailable for some tracks.
open.spotify.com/get_songSearches the Apple Music song catalog by title and artist words, returning matching tracks in relevance order with prices and previews when available.
music.apple.com/search_songsGets a public SoundCloud track and its stats from a title and optional artist, or from a track link. Search picks the artist's matching upload with the most plays; unavailable fields are null.
soundcloud.com/get_trackReturns an artist's Billboard Hot 100 song history or Billboard 200 album history: chart totals (entries, No. 1 hits, top 10 hits) and each title's debut, peak and weeks on chart, most recent debut first.
billboard.com/get_artist_chart_historyLooks up a Last.fm artist by name and returns listening statistics, profile, top tracks and albums, similar artists, and upcoming events.
last.fm/get_artistGets an artist's upcoming concerts and tour dates on Songkick, optionally filtered by country, with ticket links and start times when listed.
songkick.com/get_artist_tour_dates