Accessing MP3 metadata with Python [closed]
Asked Answered
C

16

152

Is there a maintained package I can use to retrieve and set MP3 ID3 metadata using Python?

Cohbert answered 12/8, 2008 at 15:16 Comment(2)
eyed3.readthedocs.io/en/latestAlto
This is my attempt at deciphering the meta... github.com/JayRizzo/MP3Player/blob/master/mp3TagEditor.pyDying
S
131

I used eyeD3 the other day with a lot of success. I found that it could add artwork to the ID3 tag which the other modules I looked at couldn't. You'll have to install using pip or download the tar and execute python setup.py install from the source folder.

Relevant examples from the website are below.

Reading the contents of an mp3 file containing either v1 or v2 tag info:

 import eyeD3
 tag = eyeD3.Tag()
 tag.link("/some/file.mp3")
 print tag.getArtist()
 print tag.getAlbum()
 print tag.getTitle()

Read an mp3 file (track length, bitrate, etc.) and access it's tag:

if eyeD3.isMp3File(f):
     audioFile = eyeD3.Mp3AudioFile(f)
     tag = audioFile.getTag()

Specific tag versions can be selected:

 tag.link("/some/file.mp3", eyeD3.ID3_V2)
 tag.link("/some/file.mp3", eyeD3.ID3_V1)
 tag.link("/some/file.mp3", eyeD3.ID3_ANY_VERSION)  # The default.

Or you can iterate over the raw frames:

 tag = eyeD3.Tag()
 tag.link("/some/file.mp3")
 for frame in tag.frames:
    print frame

Once a tag is linked to a file it can be modified and saved:

 tag.setArtist(u"Cro-Mags")
 tag.setAlbum(u"Age of Quarrel")
 tag.update()

If the tag linked in was v2 and you'd like to save it as v1:

 tag.update(eyeD3.ID3_V1_1)

Read in a tag and remove it from the file:

 tag.link("/some/file.mp3")
 tag.remove()
 tag.update()

Add a new tag:

 tag = eyeD3.Tag()
 tag.link('/some/file.mp3')    # no tag in this file, link returned False
 tag.header.setVersion(eyeD3.ID3_V2_3)
 tag.setArtist('Fugazi')
 tag.update()
Splanchnology answered 19/9, 2008 at 14:30 Comment(10)
eyeD3 is also GPL... so if like me you plan to use it on your program you must release your program as a free program also... darn it with these people, why can't they release under LGPL?Terreverte
@Ciantic: ID3 tags are extremely simple, why don't you make a library yourself and release it under BSD? Furthermore, this people don't own you anything in the first place. Look here diveintopython.org/object%5Foriented%5Fframework/index.htmlPharyngo
@voyager, ID3v1 tags are simple, ID3v2 tags are complicated as hell... And now I have created BSD wrapper for pytagger github.com/Ciantic/songdetails I have not tagged it yet as released, but it works.Terreverte
In the newer version, use import eyed3 (lowercase d).Flagon
@voyager - diveintopython link is dead.Tory
Note that these notes are for an older version of eyed3 and won't work well anymore. For example, the link() function has gone away and attributes are set declaratively now, without the setters.Happenstance
Unfortunately, most of these commands are outdated now and even the updated eyed3 throws errors for common MP3 files. Better to use the mutagen class EasyID3 as shown in this answer.Jollity
What about editing (changing) cover arts of music??Extremism
Even LGPL is not useable anymore, we need MIT or Apache if it should be useable in any store app because they now all do code signing.Adorno
@Terreverte people are not obligated to do work for free on license making easy to profit without giving anything back (people are also allowed to work for free for you, but not obligated)Greathearted
M
40

I've used mutagen to edit tags in media files before. The nice thing about mutagen is that it can handle other formats, such as mp4, FLAC etc. I've written several scripts with a lot of success using this API.

Moloch answered 14/8, 2008 at 9:46 Comment(2)
code.google.com/p/mutagen - Also note that Mutagen is GPL, so that is no-no for most of the projects.Terreverte
Mutagen is nice, however I'm missing a uniform way to get the artist, title genre etc. - you end up having to know the various keys, which are format dependant. TIT2 for mp3, title for ogg, \xa9nam for mp4, Title for WMA etc. - that sucks.Flews
J
35

A problem with eyed3 is that it will throw NotImplementedError("Unable to write ID3 v2.2") for common MP3 files.

In my experience, the mutagen class EasyID3 works more reliably. Example:

from mutagen.easyid3 import EasyID3

audio = EasyID3("example.mp3")
audio['title'] = u"Example Title"
audio['artist'] = u"Me"
audio['album'] = u"My album"
audio['composer'] = u"" # clear
audio.save()

All other tags can be accessed this way and saved, which will serve most purposes. More information can be found in the Mutagen Tutorial.

Jollity answered 24/1, 2016 at 0:7 Comment(2)
github.com/tooxie/shiva-server/issues/14 said “The eyeD3 library was replaced by Mutagen"Psychophysics
There's a workaround for the eyeD3 error you mentioned. You just need to call the tag's clear() method before performing any attribute assignments (if you need to carry over any original tag values, make a copy of the audio's tag object before clearing it). clear() resets all the tag data and creates a new one using the default ID3 tag version that is compatible with eyeD3Horrific
B
13

What you're after is the ID3 module. It's very simple and will give you exactly what you need. Just copy the ID3.py file into your site-packages directory and you'll be able to do something like the following:

from ID3 import *
try:
  id3info = ID3('file.mp3')
  print id3info
  # Change the tags
  id3info['TITLE'] = "Green Eggs and Ham"
  id3info['ARTIST'] = "Dr. Seuss"
  for k, v in id3info.items():
    print k, ":", v
except InvalidTagError, message:
  print "Invalid ID3 tag:", message
Bronk answered 13/8, 2008 at 0:44 Comment(1)
Just a note. This module is very old (2002) and doesn's support V2 of ID3 tagsFrankie
S
9

After trying the simple pip install route for eyeD3, pytaglib, and ID3 modules recommended here, I found this fourth option was the only one to work. The rest had import errors with missing dependencies in C++ or something magic or some other library that pip missed. So go with this one for basic reading of ID3 tags (all versions):

https://pypi.python.org/pypi/tinytag/0.18.0

from tinytag import TinyTag
tag = TinyTag.get('/some/music.mp3')

List of possible attributes you can get with TinyTag:

tag.album         # album as string
tag.albumartist   # album artist as string
tag.artist        # artist name as string
tag.audio_offset  # number of bytes before audio data begins
tag.bitrate       # bitrate in kBits/s
tag.disc          # disc number
tag.disc_total    # the total number of discs
tag.duration      # duration of the song in seconds
tag.filesize      # file size in bytes
tag.genre         # genre as string
tag.samplerate    # samples per second
tag.title         # title of the song
tag.track         # track number as string
tag.track_total   # total number of tracks as string
tag.year          # year or data as string

It was tiny and self-contained, as advertised.

Saintpierre answered 16/4, 2018 at 1:34 Comment(3)
newer version for tinytag : pypi.org/project/tinytagChequer
best solution! thanksLovelovebird
As of 2022, it only supports reading the attributes and also doesn't have BPM attribute to be queried.Intoxicating
U
8

check this one out:

https://github.com/Ciantic/songdetails

Usage example:

>>> import songdetails
>>> song = songdetails.scan("data/song.mp3")
>>> print song.duration
0:03:12

Saving changes:

>>> import songdetails
>>> song = songdetails.scan("data/commit.mp3")
>>> song.artist = "Great artist"
>>> song.save()
Unreality answered 30/12, 2010 at 1:40 Comment(0)
B
7

Just additional information to you guys:

take a look at the section "MP3 stuff and Metadata editors" in the page of PythonInMusic.

Boutte answered 8/7, 2011 at 8:24 Comment(0)
C
7

easiest method is songdetails..

for read data

import songdetails
song = songdetails.scan("blah.mp3")
if song is not None:
    print song.artist

similarly for edit

import songdetails
song = songdetails.scan("blah.mp3")
if song is not None:
    song.artist = u"The Great Blah"
    song.save()

Don't forget to add u before name until you know chinese language.

u can read and edit in bulk using python glob module

ex.

import glob
songs = glob.glob('*')   # script should be in directory of songs.
for song in songs:
    # do the above work.
Carlcarla answered 11/8, 2016 at 9:5 Comment(0)
R
7

I used tinytag 1.3.1 because

  1. It is actively supported:
1.3.0 (2020-03-09):
added option to ignore encoding errors ignore_errors #73
Improved text decoding for many malformed files
  1. It supports the major formats:
MP3 (ID3 v1, v1.1, v2.2, v2.3+)
Wave/RIFF
OGG
OPUS
FLAC
WMA
MP4/M4A/M4B
  1. The code WORKED in just a few minutes of development.
from tinytag import TinyTag

fileNameL ='''0bd1ab5f-e42c-4e48-a9e6-b485664594c1.mp3
0ea292c0-2c4b-42d4-a059-98192ac8f55c.mp3
1c49f6b7-6f94-47e1-a0ea-dd0265eb516c.mp3
5c706f3c-eea4-4882-887a-4ff71326d284.mp3
'''.split()

for fn in fileNameL:
    fpath = './data/'+fn
    tag = TinyTag.get(fpath)
    print()
    print('"artist": "%s",' % tag.artist)
    print('"album": "%s",' % tag.album)
    print('"title": "%s",' % tag.title)
    print('"duration(secs)": "%s",' % tag.duration)

  • RESULT
JoeTagPj>python joeTagTest.py

"artist": "Conan O’Brien Needs A Friend",
"album": "Conan O’Brien Needs A Friend",
"title": "17. Thomas Middleditch and Ben Schwartz",
"duration(secs)": "3565.1829583532785",

"artist": "Conan O’Brien Needs A Friend",
"album": "Conan O’Brien Needs A Friend",
"title": "Are you ready to make friends?",
"duration(secs)": "417.71840447045264",

"artist": "Conan O’Brien Needs A Friend",
"album": "Conan O’Brien Needs A Friend",
"title": "Introducing Conan’s new podcast",
"duration(secs)": "327.22187551899646",

"artist": "Conan O’Brien Needs A Friend",
"album": "Conan O’Brien Needs A Friend",
"title": "19. Ray Romano",
"duration(secs)": "3484.1986772305863",

C:\1d\PodcastPjs\JoeTagPj>
Recurrence answered 10/3, 2020 at 21:2 Comment(1)
Looks like the start to a good library. Unfortunately they do not yet support all the tags, specifically USLT and SYLT for lyrics.Televisor
T
6

I looked the above answers and found out that they are not good for my project because of licensing problems with GPL.

And I found out this: PyID3Lib, while that particular python binding release date is old, it uses the ID3Lib, which itself is up to date.

Notable to mention is that both are LGPL, and are good to go.

Terreverte answered 20/12, 2009 at 19:32 Comment(0)
M
5

A simple example from the book Dive Into Python works ok for me, this is the download link, the example is fileinfo.py. Don't know if it's the best, but it can do the basic job.

The entire book is available online here.

Marmoreal answered 12/8, 2008 at 15:37 Comment(3)
That example is a bit outdated now, both in terms of python version and in terms of ID3 version...Ralline
both links are no longer working. (I know the answer is 9 years old) If you are looking for the online book "Dive into Python", here is the current linkUnperforated
That link is also no longer working. The best I could quickly google now is github.com/diveintomark/diveintopython3Henrik
C
3

The first answer that uses eyed3 is outdated so here is an updated version of it.

Reading tags from an mp3 file:

 import eyed3

 audiofile = eyed3.load("some/file.mp3")
 print(audiofile.tag.artist)
 print(audiofile.tag.album)
 print(audiofile.tag.album_artist)
 print(audiofile.tag.title)
 print(audiofile.tag.track_num)

An example from the website to modify tags:

 import eyed3

 audiofile = eyed3.load("some/file.mp3")
 audiofile.tag.artist = u"Integrity"
 audiofile.tag.album = u"Humanity Is The Devil"
 audiofile.tag.album_artist = u"Integrity"
 audiofile.tag.title = u"Hollow"
 audiofile.tag.track_num = 2

An issue I encountered while trying to use eyed3 for the first time had to do with an import error of libmagic even though it was installed. To fix this install the magic-bin whl from here

Claxton answered 8/4, 2018 at 15:52 Comment(1)
This answer misses audiofile.tag.save() call for saving the modified tagLotti
S
2

I would suggest mp3-tagger. Best thing about this is it is distributed under MIT License and supports all the required attributes.

- artist;
- album;
- song;
- track;
- comment;
- year;
- genre;
- band;
- composer;
- copyright;
- url;
- publisher.

Example:

from mp3_tagger import MP3File

# Create MP3File instance.
mp3 = MP3File('File_Name.mp3')

# Get all tags.
tags = mp3.get_tags()
print(tags)

It supports set, get, update and delete attributes of mp3 files.

Seal answered 26/6, 2018 at 13:50 Comment(0)
A
2

using https://github.com/nicfit/eyeD3

import eyed3
import os

for root,  dirs, files in os.walk(folderp):
    for file in files:
        try:
            if file.find(".mp3") < 0:
                continue
            path = os.path.abspath(os.path.join(root , file))
            t = eyed3.load(path)
            print(t.tag.title , t.tag.artist)
            #print(t.getArtist())
        except Exception as e:
            print(e)
            continue
Aerie answered 6/2, 2020 at 23:51 Comment(1)
Can you provide and explanation for this?Recess
D
1

It can depend on exactly what you want to do in addition to reading the metadata. If it is just simply the bitrate / name etc. that you need, and nothing else, something lightweight is probably best.

If you're manipulating the mp3 past that PyMedia may be suitable.

There are quite a few, whatever you do get, make sure and test it out on plenty of sample media. There are a few different versions of ID3 tags in particular, so make sure it's not too out of date.

Personally I've used this small MP3Info class with luck. It is quite old though.

http://www.omniscia.org/~vivake/python/MP3Info.py

Denni answered 12/8, 2008 at 15:37 Comment(0)
L
1

After some initial research I thought songdetails might fit my use case, but it doesn't handle .m4b files. Mutagen does. Note that while some have (reasonably) taken issue with Mutagen's surfacing of format-native keys, that vary from format to format (TIT2 for mp3, title for ogg, \xa9nam for mp4, Title for WMA etc.), mutagen.File() has a (new?) easy=True parameter that provides EasyMP3/EasyID3 tags, which have a consistent, albeit limited, set of keys. I've only done limited testing so far, but the common keys, like album, artist, albumartist, genre, tracknumber, discnumber, etc. are all present and identical for .mb4 and .mp3 files when using easy=True, making it very convenient for my purposes.

Lowpressure answered 12/7, 2015 at 23:17 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.