LyricsGenius: a Python client for the Genius.com API
Download song lyrics and metadata from Genius.com 🎶🎤
At a glance
- What is it?
- LyricsGenius is a small Python library that searches Genius.com for songs, artists and albums and downloads their lyrics and metadata, with a command line interface for batch saving. It suits a researcher doing sentiment analysis or translation work on lyrics, and it needs a free Genius account for an access token.
- Who is it for?
- Adopt LyricsGenius if you need a reproducible way to pull song lyrics and metadata from Genius for analysis, and you are happy to work with a library whose parsing follows Genius's own page structure. Skip it if you need a commercial lyrics service with a licence, since the terms of the source site are separate from the MIT licence of this client.
- Can I use it commercially?
- Yes. MIT is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
- Is it still maintained?
- Yes. The repository last received commits 16 days ago.
- What is it written in?
- Mainly Python, according to GitHub's language statistics.
Answers come from the project's GitHub data, last synced on October 22, 2026, and from our analysis. They are not legal advice.
Editorial analysis
What the library is
LyricsGenius provides a simple interface to the song, artist and lyrics data stored on Genius.com. It is a client, not a scraper in the general sense, because it goes through the Genius API rather than crawling the site, and the API requires a token. The library is written in Python, licensed MIT, with the primary language recorded as Python and the documentation hosted on Read the Docs. The last push was on 2026-10-09 and the releases are v3.15.0 on 2026-10-09, v3.14.0 and v3.13.0 both on 2026-09-22, which is a quick pace. The dependency list is short and telling, with beautifulsoup4 and requests as the only runtime requirements, which means the HTML parsing of the lyrics page is the one place where the library is coupled to how Genius renders a song. The homepage is the author's article on scraping Genius lyrics.
Setup, the token, and the environment variable
Before using the package you need a free account that authorizes access to the Genius API, and that account provides an `access_token` which is required by the package. The install is a pip command from PyPI:
pip install lyricsgeniusor from GitHub:
pip install git+https://github.com/johnwmillr/LyricsGenius.gitThe library requires Python 3.11 or greater. The token is supplied to the `Genius` constructor, and if you do not pass one the library looks for an environment variable called `GENIUS_ACCESS_TOKEN` and attempts to use that for authentication. That fallback is the one to prefer in anything you deploy, since it keeps the credential out of the source:
import lyricsgenius
genius = lyricsgenius.Genius(token)or, reading the environment:
genius = Genius()The token is a per-client secret from a free account, and the README is clear that the account is what authorizes the access, so registering a client is the step that turns this from a hobby script into something that keeps working.
Searching for an artist and their songs
The artist search is the main entry point, and it has a parameter that matters more than it looks:
artist = genius.search_artist("Andy Shauf", max_songs=3, sort="title")
print(artist.songs)By default, `search_artist()` only returns songs where the given artist is the primary artist. There are instances where it is desirable to get all of the songs the artist appears on, and that is what the `include_features` argument is for, set to `True`:
artist = genius.search_artist("Andy Shauf", max_songs=3, sort="title", include_features=True)
print(artist.songs)The default is the right one for most analysis work, since a featured appearance is a different data point from a track by that artist, and including them silently changes the denominator of any statistic you compute over the catalogue. From the artist you can pull a single song, either through the artist object or through the client, and read its lyrics:
song = artist.song("To You")
# or:
# song = genius.search_song("To You", artist.name)
print(song.lyrics)The artist object also accepts song names directly, so `artist.add_song("To You")` works as well as passing a song object.
Saving lyrics, and the options that decide what you get
The saving side is where the library earns its keep for bulk work. An artist's songs go to a JSON file with `artist.save_lyrics()`, and an album is found and saved with `genius.search_album("The Party", "Andy Shauf")` followed by `album.save_lyrics()`. Three configuration attributes decide what ends up in that output, and they are set on the client:
genius.remove_section_headers = True # Remove section headers (e.g. [Chorus]) from lyrics when searching
genius.skip_non_songs = False # Include hits thought to be non-songs (e.g. track lists)
genius.excluded_terms = ["(Remix)", "(Live)"] # Exclude songs with these words in their titleThe section header option matters if you are doing anything with the raw text, because a chorus marker is a structural annotation rather than a lyric and will show up in a word count or a sentiment score. The `skip_non_songs` option is off by default, so hits that are track lists are included unless you exclude them. And `excluded_terms` is a title filter, which is how you drop the remix and live versions that would otherwise flood a catalogue search with the same song in a dozen takes. By default the library is silent, and progress logging is enabled with `lyricsgenius.enable_logging()`, which defaults to DEBUG and takes `logging.INFO` for less output.
The command line interface
The package can be called from the command line, and this is the path most bulk jobs take, since it avoids writing a script for a one-off download. You export the token and then use `python -m lyricsgenius`:
export GENIUS_ACCESS_TOKEN="my_access_token_here"
python -m lyricsgenius --help
# Print a song's lyrics to stdout in text format
python -m lyricsgenius song "Check the Rhyme" "A Tribe Called Quest" --format txt
# Save a song's lyrics in JSON format
python -m lyricsgenius song "Begin Again" "Andy Shauf" --format json --save
# Save a song's lyrics with a custom filename
python -m lyricsgenius song "Begin Again" "Andy Shauf" --format json --save --output-file my_song
# Save an artist's lyrics to text files (stopping after 2 songs)
python -m lyricsgenius artist "The Beatles" --max-songs 2 --format txt --saveThe `song` subcommand takes a title and an artist, the `artist` subcommand takes an artist name, and `--format` accepts `txt`, `json` or both. `--save` writes to disk rather than stdout, `--output-file` names the file, and `--max-songs` bounds an artist run, which is the flag you want when you are rate limited or when you only need a sample.
What the library was used for, and the practical limits
The README lists example projects that show what the library enables, and they are all analysis tasks. There is a textual analysis of popular country music, a neural machine translation project explaining the meaning behind lyrics, a study of what makes some blink-182 songs more popular than others, sentiment analysis on hip-hop lyrics, a question of whether country music drinks more than other genres, and an analysis of 49 years of lyrics asking why the songs are so angry. That list is a good argument for the library and also a good description of its limits. The lyrics come from Genius's own page, and the page's lyrics are community-contributed and periodically corrected, so a corpus built this way is a snapshot of a wiki rather than a fixed text. The library's HTML parsing with BeautifulSoup is coupled to that page structure, and a change to how Genius renders a song can break the extraction. And the terms on which Genius's content is made available are a separate question from the MIT licence of this client, which covers the code and not the lyrics it retrieves. The token requirement also means your access is tied to a registered client, so a bulk job needs to be paced rather than fired.
Releases, and the tooling around the source
The release process is worth a note because it explains a detail you would otherwise find confusing. Releases are driven by tags, and the package version is derived from the tag, so there is no version to bump anywhere in the repository. You tag a commit on master and push the tag:
git tag v3.15.0
git push origin v3.15.0That builds the package, publishes it to PyPI and creates the matching GitHub release, and a run that fails partway can simply be re-run. The pyproject file confirms the mechanism, with hatchling and hatch-vcs as the build backend and a `[tool.hatch.version]` section whose source is `vcs`. The repository root shows the tooling in use, with a `pyproject.toml`, a `uv.lock`, a `tox.ini`, a `mypy.ini`, a `.ruff.toml` and a `.pre-commit-config.yaml`. The optional dependency groups are `docs` for Sphinx and the `checks` group for flake8, bugbear, pygments and tox, with a dev group adding mypy, pre-commit, pytest and ruff. There is also a configured TestPyPI index in the pyproject, with the publish URL set to the legacy endpoint, which is how a release gets tested before it goes out.
Editorial conclusion
Adopt LyricsGenius if you need a reproducible way to pull song lyrics and metadata from Genius for analysis, and you are happy to work with a library whose parsing follows Genius's own page structure. Skip it if you need a commercial lyrics service with a licence, since the terms of the source site are separate from the MIT licence of this client. Before you start, sign up for a free Genius account to get an access token, export it as `GENIUS_ACCESS_TOKEN` or pass it to the `Genius` constructor, and note that the package requires Python 3.11 or newer.
Frequently asked questions
Do I need a Genius account to use LyricsGenius?
Yes. Before using the package you need a free account that authorizes access to the Genius API, and that account provides the access_token the package requires. You can pass it to the Genius constructor or set the GENIUS_ACCESS_TOKEN environment variable.
How do I install LyricsGenius?
With `pip install lyricsgenius` from PyPI, or `pip install git+https://github.com/johnwmillr/LyricsGenius.git` for the GitHub version. The package requires Python 3.11 or greater.
What is the difference between include_features in search_artist?
By default search_artist() only returns songs where the given artist is the primary artist. Setting include_features to True returns all of the songs the artist appears on, which matters when you want featured appearances included in a catalogue.
How do I save lyrics from the command line?
Use `python -m lyricsgenius song "Begin Again" "Andy Shauf" --format json --save` to save a single song, or `python -m lyricsgenius artist "The Beatles" --max-songs 2 --format txt --save` for an artist. The --output-file flag names the file and the --format flag accepts txt, json or both.
Can I exclude section headers and remixes from downloaded lyrics?
Yes. Set genius.remove_section_headers to True to strip markers like [Chorus], set genius.skip_non_songs to False to include hits that look like track lists, and use genius.excluded_terms such as ["(Remix)", "(Live)"] to exclude songs with those words in the title.
Official sources
Add this badge to your README
If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.
[](https://hysenlabs.com/projects/johnwmillr-lyricsgenius)Was this useful?