MusicDatabase

This class manages the MusicDB Database the core of MusicDB. It caches information from the filesystem and provides augmentation of those files. This database handles the following components:

All database entries (= rows) are handled as dictionaries. The key of the dictionary corresponds to the column name of the database.

If an entry of this dictionary got changed directly, the following methods can be used to store the changes in the database. This is not the recommended way because the content gets not checked. The preferred way to change any data is using the related method described in the following sections.

Validity of columns

Some column values are generated when importing data. The way these values are well defined. After creating the values, they may be changed by the user or other tools. Affected are all the following columns:

  • All name-columns

  • artworkpath of albums

  • thumbnailpath of videos

For example, the artwork path is generated by the artist and album name. So when working with albums, instead of using the artwork path value, the path could be regenerated by the artist and album names. This is not recommended! In case an other tool changes the artwork path entry, this may lead to a path of a no longer existing artwork file.

Adding a Column

When a new column shall be added, the following steps are necessary.

  1. Shutdown the server: systemctl stop musicdb

  2. Backup the database: sqlite3 music.db .dump > backup/music.db.bak

  3. Update this file.

  4. Update the SQL file sql/music.sql

  5. Modify the database:
    1. Open: sqlite3 music.db

    2. Add column. For example ALTER TABLE songs ADD COLUMN feature INTEGER DEFAULT 0;

    3. Quit: .quit

Furthermore be sure that all command line modules and API modules handle the new added column, and so new added feature correct. For example, methods creating a new entry in the modified table may be adopted.

Songs Table

The columns of the songs table are the following:

songid

albumid

artistid

name

path

number

cd

disabled

playtime

bitrate

likes

dislikes

favorite

lyricsstate

checksum

lastplayed

liverecording

badaudio

checksum (Text)

This is the sha256 hash value of the file addressed by path. The checksum will be calculated like shown in the following example:

songpath = song["path"]
songfile = open(songpath, "rb")

with open(songpath, "rb") as songfile:
    checksum = hashlib.sha256(songfile.read()).hexdigest()

song["checksum"] = checksum

The hash function will not be changed in future. This is OK as long as the hash value will not be used for security related things!

It can happen, that the value is empty (""). This only means that the checksum of the song was not calculated yet. In this case, just calculate it, and write it into the database.

lastplayed (Integer)

This value holds the information, when the song was played the last time. The time gets represented as an integer (unixtime).

Song Relates Methods

The following methods exist to handle song entries in the database:

Videos Table

The columns of the videos table are the following:

videoid

songid

albumid

artistid

name

path

disabled

playtime

origin

release

added

codec

xresolution

yresolution

framesdirectory

thumbnailfile

previewfile

likes

dislikes

favorite

liverecording

badaudio

checksum

lastplayed

lyricsvideo

bgcolor

fgcolor

hlcolor

vbegin

vend

songid, albumid (Integer)

These are references to an album the videos was included in, and/or the song the video belongs to. In case the album and/or song is not included in the collection, these values can be NULL.

added (Integer)

Unix-Time when the video was added to the database

release (Integer)

Year when the video was released. This year may be different to the release year of the album or song

codec (Text)

Like "h264"

checksum (Text)

This is the sha256 hash value of the file addressed by path. The checksum will be calculated like shown in the following example:

videopath = video["path"]
videofile = open(videopath, "rb")

with open(videopath, "rb") as videofile:
    checksum = hashlib.sha256(videofile.read()).hexdigest()

video["checksum"] = checksum

The hash function will not be changed in future. This is OK as long as the hash value will not be used for security related things!

It can happen, that the value is empty (""). This only means that the checksum of the song was not calculated yet. In this case, just calculate it, and write it into the database.

lastplayed (Integer)

This value holds the information, when the song was played the last time. The time gets represented as an integer (unixtime).

Video Relates Methods

The following methods exist to handle video entries in the database:

Albums Table

Data structure:

albumid

artistid

name

path

numofsongs

numofcds

origin

release

artworkpath

bgcolor

fgcolor

hlcolor

added

hidden

added (Integer)

This is the time the album got added to the collection as unixtime rounded to an integer (full seconds)

hidden (Integer)

When 1, the album will not be included in some SQL query results. See the documentation of the specific methods to identify if hidden albums are included or not.

Origin

Valid values:

  • "iTunes"

  • "bandcamp"

  • "music163" aka 网易云音乐

  • "CD" as fallback for unknown flac files

  • "internet" as fallback for any other unknown files

Artists Table

Database structure:

Lyrics Table

Lyrics state is part of the songs table. The lyrics itself are stored in the lyrics table with the following layout:

songid

lyrics

Lyrics are stored in a simple markup language:

  • :: ref starts a section for the refrain

  • :: comment starts a section for comments that are not part of the lyrics

  • :: ends a section

  • <<…>> “highlight” text - use secondary color for printing this text

A lyrics entry could look like the following example:

:: comment
Just a dummy text
::

Lorem ipsum dolor sit amet,
consetetur sadipscing elitr,
sed diam nonumy eirmod tempor
invidunt ut labore et dolore
magna aliquyam erat,
sed diam voluptua.

:: ref
At vero eos et accusam et justo duo dolores et ea rebum.
Stet clita kasd gubergren,
no sea takimata sanctus est Lorem ipsum dolor sit amet.
::

<< (5 times) >>

The lyrics column can have the following states:

  • SONG_LYRICSSTATE_EMPTY - There are no lyrics set yet

  • SONG_LYRICSSTATE_FROMFILE - The lyrics set come from the metatags of the song file

  • SONG_LYRICSSTATE_FROMNET - The lyrics were grabbed from the internet by a crawler

  • SONG_LYRICSSTATE_FROMUSER - The lyrics were reviewed by the user. This noted the highest state of quality for lyrics.

  • SONG_LYRICSSTATE_NONE - There are no lyrics for this song - it is an instrumental song.

Tags Table

In this section, the tag management is described. A Toxi scheme is used to implement the tag system in MusicDB. This means there are n+2 tables:

  1. A Table with the definition of a tag,

  2. a table that maps the tag to an entity,

  3. and n tables with entities with a global unique identifier.

MusicDB does not have global unique identifier for artists, albums an genres, so instead of one mapping table, there are two. One for the songs, and one for the albums. Tags for Artists are not expected. If there will be a need later on, it an easy be implemented by adding a third mapping table and/or introducing new classes of tags. A tag must be identifiable by the combination of its name and class.

Tag Definition Table

0

1

2

3

4

5

6

7

8

TagID

Name

Class

ParentID

IconType

Icon

Color

PosX

PosY

TagID (Integer)

ID of the tag that gets generated by the database

Name (String)

Name of the tag. It will be used inside the MusicDB code or by the UI as it is stored in the database. So, the name is set as it shall be displayed. It must also be a unique name inside its class.

Class (Integer)

ID of the class:

  • 1 - Genre

  • 2 - Subgenre

  • 3 - Mood

ParentID (Integer / None)

ID of a related tag. In case of subgenre, the main genres ID would be the ParentID. Important: A parent tag must always be of class Genre. And only Subgenre can and must have a parent!

IconType (Integer / None)

If None the icon-column will be ignored. Otherwise it defines the type of icon:

  • 1 - Unicode character

  • 2 - HTML tag for special fonts: <i class="fa fa-beer"></i>

  • 3 - png image Future feature - specification incomplete

  • 4 - svg image Future feature - specification incomplete

Icon (Text / None)

A shorter version of the name. The Icon must be compatible to the specified type.

Color (Text / None)

A HTML-like color code that can be used to highlight a very special tag. Do not use this feature too much, it can break the UI visual design.

PosX, PosY (Integer / None)

The (X;Y) Position of the Name or the Icon in a grid if the tags were presented as grid in an UI. The tag position gets stored in the global database to make sure that every UI provides a similar layout of the tags to make it more usable. (0;0) is the upper left corner. If not a grid but a list gets described, posx determines the position and posy is set to NULL.

Tag Mapping Table

The mapping-tables have all the same layout

Table Name

0

1

2

3

4

songtags

EntryID

SongID

TagID

Confidence

Approval

albumtags

EntryID

AlbumID

TagID

Confidence

Approval

EntryID (Integer)

ID of the entry in the mapping-table

TagID (Integer)

ID of the tag in the Tag-Definition-Table

xxxID (Integer)

ID of the song or album entry in the related tables

Confidence (Floating point, Default: 1.0)

Confidence that the tag is correct. This is important in case an AI set the tag (See Approval). Otherwise this column can be ignored. - Ignoring means setting it to 1.0!

Approval (Integer, Default: 1)

Three stages to approve the tag.

  • 0 - Set by AI. This tag may be wrong. The Confidence value is relevant in this case.

  • 1 - Set by the User. Confidence must be set to 1.0

  • 2 - Can be used for training. This Song/Album is a good representation for this tag. It can be used to train an AI.

MusicDatabase Class

class musicdb.lib.db.musicdb.MusicDatabase(path)[source]

This class is the interface to the Music Database. It is derived from musicdb.lib.db.database.Database.

Parameters:

path – path to the music database

Raises:

ValueError – When the version of the database does not match the expected version. (Updating MusicDB may failed)

AddAlbum(artistid, name, path)[source]

Creates a new entry for an album.

Parameters:
  • artistid – ID of the artist who is related to the album

  • name (str) – name of album

  • path (str) – relative path of the album

Returns:

None

Raises:
  • TypeError – When path or name is not of type string, and artistid not a string or an integer

  • ValueError – When artistid is not a decimal number

AddArtist(name, path)[source]

Adds a new artist into the artists table

Parameters:
  • name (str) – name of the artist

  • path (str) – relative path of the artist directory

Returns:

None

Raises:

TypeError – If path is not of type str

AddFullSong(song)[source]

This method creates a new entry for a song and adds all its attributes into the database. Creating the song is done by calling AddSong(). When the song was added a new song ID is generated by the database engine. The new entry gets read from the database. Then, the new ID is set as song ID to the dictionary given as argument. After that, the whole song dictionary gets written to the database via WriteSong()

In case adding the song fails on half the way, the new added entry gets deleted. As long as nothing references the song entry, it is no problem to remove it. So, when this method returns False Nothing changed in the database.

Parameters:

song – A complete dictionary with all keys of a MusicDB Song entry for the database

Returns:

True on success, otherwise False which indicates that nothing changed in the database.

AddFullVideo(video)[source]

This method creates a new entry for a video and adds all its attributes into the database. Creating the song is video by calling AddVideo(). When the video was added a new song ID is generated by the database engine. The new entry gets read from the database. Then, the new ID is set as song ID to the dictionary given as argument. After that, the whole song dictionary gets written to the database via WriteVideo()

In case adding the video fails on half the way, the new added entry gets deleted. As long as nothing references the video entry, it is no problem to remove it. So, when this method returns False Nothing changed in the database.

Parameters:

video – A complete dictionary with all keys of a MusicDB Song entry for the database

Returns:

True on success, otherwise False which indicates that nothing changed in the database.

AddSong(artistid, albumid, name, path)[source]

This method creates a new database entry for a song and sets the most important values.

If a song with the same path is already in the database, its artistid, albumid and name gets compared to the arguments. If they match, everything is fine and the method returns. If they differ, an AssertionError gets raised. Adding an existing song is a bug! Even if this method allows it under some conditions, this should not be exploited!

Parameters:
  • artistid (int) – ID of the artist of this song

  • albumid (int) – ID of the album of this song

  • name (string) – Name of the song

  • path (string) – Path of the song file relative to the music root directory

Returns:

None

Raises:
  • TypeError – If one of the arguments is None

  • ValueError – If song is already in the database and does not match the other parameters

AddVideo(artistid, name, path)[source]

This method creates a new database entry for a video and sets the most important values (Artistid, name and path).

If a video with the same path is already in the database, its artistid, path and name gets compared to the arguments. If they match, everything is fine and the method returns. If they differ, an AssertionError gets raised. Adding an existing video is a bug! Even if this method allows it under some conditions, this should not be exploited!

Parameters:
  • artistid (int) – ID of the artist of this video

  • name (string) – Name of the video

  • path (string) – Path of the video file relative to the music root directory

Returns:

None

Raises:
  • TypeError – If one of the arguments is None

  • ValueError – If song is already in the database and does not match the other parameters

CreateTag(tagname, tagclass, parentid=None)[source]

This method creates a new tag in the tags-table.

If the tag already exists in its class, it will not be created.

Parameters:
  • tagname (str) – Name of the new tag. This is also the name that gets displayed in the GUI.

  • tagclass (int) – Defines the class of the tag.

  • parentid (int) – Optional parent relation to other tags - Mandatory for subgenre

Returns:

None

Raises:
  • TypeError – if tagname is not a string or parentid does not have the value it should have regarding the specification

  • ValueError – When tagclass has an invalid value

DeleteTag(tagname, tagclass)[source]

See DeleteTagByName()

DeleteTagById(tagid)[source]

This method deletes a tag addressed by its tag ID. Before deleting the tag, this tag as well as its child-tags (sub-genre tag) will be removed from all songs, albums and videos.

Warning

This method has a very different behavior compared to DeleteTagByName()!

Parameters:

tagid (int) – ID of the tag to delete

Returns:

None

Raises:

TypeError – When tagid is not an integer

DeleteTagByName(tagname, tagclass)[source]

Deletes an entry from the tags-table with the name tagname and that belongs to tagclass.

Warning

This method does NOT delete child tags or the relation between the tag and songs or albums. You should only delete new created tags that are not used!

Parameters:
  • tagname (str) – Name of the tag that shall be deleted.

  • tagclass (int) – Class of the name the tag belongs to.

Returns:

None

Raises:
  • TypeError – If tagname is not of type str

  • ValueError – If tagclass is not a valid class ID.

GenreListToGenreTree(genrelist)[source]
Parameters:

genrelist (list) – A list of tag IDs

Returns:

A dict with a key for each genre in genrelist and a list of each included sub genre as value

GetAlbumById(albumid)[source]

Returns an album entry if available. It also returns the entry, when the album is hidden!

Parameters:

albumid – entry ID of the album in the album table

Returns:

An album entry or None it the album does not exits

Raises:
  • TypeError – If albumid is not set

  • AssertionError – If there is more than one album with the given ID

GetAlbumByPath(path)[source]

Returns an album entry if available. It also returns the entry when the album is hidden!

Parameters:

path (str) – relative path of an album

Returns:

An album entry or None it the album does not exits.

Raises:
  • TypeError – If path is not of type str

  • AssertionError – If there is more than one album with the given path

GetAlbums(artistid=None, withsongs=False, hidden='no', genretree=None)[source]

This method returns a list with all albums in the database, or all albums of an artist if artistid is not None. If the withsongs parameter is True, for each album all songs will be included. They are added as list into each album entry under the key songs

The hidden parameter is a string that can have the following values to describe how hidden albums should be handled:

  • "no": No hidden albums included

  • "include": Hidden and not hidden albums returned

  • "only": Only return hidden albums

Hidden albums are not included!

When genretree is not None, then the albums filtered by its genres

Example

The following example prints all songs of the artist with the ID 1000

albums = musicdb.GetAlbums(artistid = 1000, withsongs = True)
for album in albums:
    for song in album["songs"]:
        print(song["name"])
Parameters:
  • artistid (int) – Optional. ID for an artist whose albums shall be returned. If None the albums get not filtered by artistid.

  • withsongs (bool) – Optional. Also return all songs of the album.

  • hidden (str) – Optional modify for handling hidden albums

  • genretree (dict) – A tree of genres and their sub genres to filter the album by genres

Returns:

A list with all non-hidden albums.

Raises:
  • TypeError – If withsongs is not of type bool

  • TypeError – If hidden is not a string

  • ValueError – When hidden has not one of the above listed values

GetAlbumsByArtistId(artistid)[source]

See GetAlbums() (GetAlbums(artistid, withsongs=False, hidden="no"))

GetAllAlbumIds(includehidden=False)[source]

Returns a list of all album Ids.

If the optional includehidden argument is not set to true, hidden albums are not included!

Parameters:

includehidden (bool) – When true, hidden albums are also included

Returns:

Returns a list of all album IDs

GetAllAlbums()[source]

See GetAlbums() (GetAlbums(artistid=None, withsongs=False, hidden="include"))

GetAllArtists()[source]

Returns a list of all artists in the artists table.

Returns:

List of all artists

GetAllSongs()[source]

See GetSongs()

GetAllTags(tagclass=None)[source]

This method returns a list of tags from the tags table. If tagclass is set, only tags of the specified class gets returned. Otherwise all tags.

Parameters:

tagclass (int) – Optional, to only get tags of the given class

Returns:

A list of tags

Raises:

ValueError – If tagclass is set (not None) with an invalid value

GetArtistById(artistid)[source]

Returns the artist by its ID

Parameters:

artistid – ID of the artist in the artist table

Returns:

The database entry of the artist or None if there is no entry for this artist directory

Raises:
  • TypeError – When artistid is not an integer or a string

  • ValueError – When artistid is a string that cannot be interpreted as a decimal number

  • AssertionError – When there is more than one entry with the same ID (This should never happen)

GetArtistByPath(path)[source]

Returns the artist by the relative path of the music directory. This is usually only a directroy name.

Parameters:

parth (str) – relative path of an artist

Returns:

The database entry of the artist or None if there is no entry for this artist directory

Raises:
  • TypeError – When path is not a string

  • AssertionError – When there is no artist with the given path

GetFilteredAlbumIds(tagfilterlist)[source]

Returns a list of album IDs of albums of a certain genre. The genre (or sub genre) is defined by the tag IDs in the tagfilterlist list. If tagfilterlist is empty, an empty list gets returned.

Hidden albums are not included. Albums without sub genre tags are included as well. Albums that match a main genre but not a sub genre are rejected.

Parameters:

tagfilterlist (list) – A list of integers representing tag IDs.

Returns:

A list of album IDs

Raises:

TypeError – When tagfilterlist is not of type list

GetFilteredAlbums(genretree)[source]

See GetAlbums() (GetAlbums(artistid=None, withsongs=False, hidden="include", genretree=genretree))

GetFilteredAlbumsByArtistId(artistid, genretree)[source]

See GetAlbums() (GetAlbums(artistid, withsongs=False, hidden="no", genretree=genretree))

GetFilteredSongIds(constraints, albumid=None)[source]

This method returns a list of song IDs of songs that fulfill certain constraints. The following constraints are possible. They must be given as dictionary. The key represents the constrain, the value behind the key represents the corresponding value of the constraint. If an album ID is given, only songs of this particular album are considered.

  • disabled (bool): If False no disables songs will be selected

  • hated (bool): If False no hated songs will be selected

  • badfile (bool): If False no songs marked as “bad file” will be selected

  • livemusic (bool): If False no songs marked as “live recording” will be selected

  • minlen (int): If set, no songs with less than minlen seconds will be selected

  • maxlen (int): If set, no songs with more than maxlen seconds will be selected

Parameters:
  • constraints (dict) – A set of constraints

  • albumid (int) – Optional album ID. If given, only songs of this album are considered.

Returns:

A list of song IDs that fulfill the given constraints

GetLyrics(songid)[source]

This method returns the lyrics of a song.

Parameters:

songid (int) – ID of the song for that the lyrics shall be returned

Returns:

The lyrics of a song or None if there are no lyrics for the song.

Raises:
  • TypeError – When sonid is not an integer or string

  • AssertionError – If there were multiple lyrics entries for the given song ID

GetRandomSong(tagfilterlist, constraints, albumid=None)[source]

This method returns a random song that fulfills several constraints.

The tagfilterlist can be either a set of genre and sub genre tag IDs or None. When tagfilterlist is None no filter gets applied. Otherwise only albums of the genres and sub genres in the list will be considered.

Selection Algorithm:

If albumid is not given, a random album gets selected first. Then a random song gets selected from the random album or given album. This gives each album the same chance to provide a song, independent from how many songs are included in an album. Hidden albums and their songs are excluded.

It must be assumed that only the album is properly tagged. When it comes to selecting a certain song, all songs are considered independent from their genre or sub genre tags as long as they do not conflict when given. So a song of a different genre or sub genre gets rejected. A song that has no genre or sub genre is considered as candidate.

When looking at tags, the confidence and approval value gets ignored for albums. For songs, only approved tags lead to rejection.

Each song gets checked if it fulfills the genre constraints. When a song has no genre IDs, it is fine. When there are genre IDs, they have to match the tagfilterlist. The same for sub genre IDs.

When there is an album of a main genre that is in the tagfilterlist, but has no sub genres, it is still considered for the song selection phase. When then, there is a song of this album that does not have a sub genre set, this song is returned as valid match. It might be of one of the wished sub genres.

digraph hierarchy { size="5,8" start [label="Start"]; albumidgiven [shape=diamond, label="Is an Album ID given?"] hasfilterlist [shape=diamond, label="len(tagfilterlist) > 0"]; getfilteredalbumids [shape=box, label="Get filtered Album IDs"]; getallalbumids [shape=box, label="Get all Album IDs"]; selectalbumid [shape=box, label="Select random Album"]; getallsongs [shape=box, label="Get Songs from Album"]; selectsong [shape=box, label="Select Song"]; start -> albumidgiven; albumidgiven -> hasfilterlist [label="No"]; hasfilterlist -> getfilteredalbumids [label="Yes"]; hasfilterlist -> getallalbumids [label="No"]; getfilteredalbumids -> selectalbumid getallalbumids -> selectalbumid albumidgiven -> getallsongs [label="Yes"]; selectalbumid -> getallsongs getallsongs -> selectsong }

Constraints:

The selected song must fulfill certain constraints given as dictionary in the constraint parameter. Possible constraints are listed in the related method GetFilteredSongIds().

Parameters:
  • tagfilterlist (list) – A list of integers representing tag IDs for genres and sub genres.

  • constraints (dict)

  • albumid (int) – When not None, a random song from that specific album (addressed by its ID) gets chosen.

Returns:

A random Song fulfilling all requirements given by the parameters of this function. None gets returned if there is no song fulfilling the constraints.

GetRandomVideo(filterlist=None, nodisabled=True, nohated=False, minlen=None, maxlen=None)[source]

This method returns a random video that fulfills several constraints.

The filterlist can be either a set of genre tag IDs or a set of genre names. When filterlist is None no filter gets applied. Otherwise only videos of the genres in the list will be considered.

Getting a random video is done by the following steps:

  1. Get video IDs of all videos in the database

  2. Translate filterlist into a list of tag IDs

  3. For each video, get its tags and compare that with the set of tag IDs from the filter. (If there is no filter list set, all video IDs are selected)

  4. Select a random video

Parameters:
  • filterlist – Optional, default value is []. A list of genre names or genre tag IDs that limits the search set. The tags have OR relations.

  • nodisabled (bool) – If True no disables songs will be selected

  • nohated (bool) – If True no hated songs will be selected

  • minlen (int) – If set, no videos with less than minlen seconds will be selected

  • maxlen (int) – If set, no videos with more than maxlen seconds will be selected

Returns:

A random MusicDB Video dictionary that fulfills the constraints, or None when there is no song fulfilling the constraints

Raises:
  • TypeError – When nodisabled or nohated are not of type bool

  • TypeError – When minlen or maxlen is not None and not of type integer

  • TypeError – When filterlist is not a list and not None

  • ValueError – When minlen is less than 0

  • ValueError – When maxlen is less than 0

GetSongById(songid)[source]

Returns a song from the database that matches the songid

Parameters:

songid (int) – ID of the song that shall be returned

Returns:

A MusicDB Song dictionary or None if there is no song with that ID

Raises:
  • TypeError – If songid is not an integer or a string

  • AssertionError – If there is more than one song with the same ID

GetSongByPath(path)[source]

Returns a song from the database that matches the path

Parameters:

path (str) – A song path relative to the music root directory

Returns:

A MusicDB Song dictionary or None if there is no song with that path

Raises:
  • TypeError – If path is None

  • AssertionError – If there is more than one song with the same path

GetSongs(albumid=None)[source]

This method returns all songs in the database if albumid is None, or all songs of an album if albumid is set.

Parameters:

albumid (int) – ID of an album or None

Returns:

A list of MusicDB Songs

GetSongsByAlbumId(albumid)[source]

See GetSongs()

GetSongsByArtistId(artistid)[source]

This method returns all song entries of an Artist.

Parameters:

artistid (int) – ID of an artist

Returns:

A list of MusicDB Songs

Raises:

TypeError – If artistid is not a decimal number of type integer or sting

GetSubgenresOfGenre(genre)[source]

This method returns a list of all sub genres connected to a specific genre with the ID or Name genre.

Parameters:

genreid (int/str) – A genre ID or genre Name for that its sub genres shall be returned

Returns:

A list of sub genres. An empty list if no sub genres exist

Raises:

TypeError – If genreid is not of type int or str

GetTagById(tagid, tagclass=None)[source]

This method returns a tag entry addressed by the tag id and tagclass. The tag class can be None to consider all classes.

Parameters:
  • tagid (int) – ID of the tag that shall be returned

  • tagclass (int) – ID of the tagclass - Default is the main genre class. If None all classes are considered.

Returns:

The row of the specified tag, or None if no tag was found

Raises:
  • ValueError – If no name or valid tagclass was given

  • TypeError – If tagname is not a string

  • AssertionError – If more than one tag was found - This should never happen!

GetTagByName(tagname, tagclass=1)[source]

This method returns a tag entry addressed by the tagname and tagclass.

Parameters:
  • tagname (str) – Name of the tag that shall be returned

  • tagclass (int) – ID of the tagclass - Default is the main genre class.

Returns:

The row of the specified tag, or None if no tag was found

Raises:
  • ValueError – If no name or valid tagclass was given

  • TypeError – If tagname is not a string

  • AssertionError – If more than one tag was found - This should never happen!

GetTagStatistics(tagid)[source]

Returns three integers telling how often the given tag is used for songs, albums and videos. It is also checked how many other tags used the tagid as parent tag.

The level of confidence or if the tag was approved for the song/video/album is not considered. All set tags are counted.

Parameters:

tagid (int) – ID of the tag to count

Returns:

songs(int), albums(int), videos(int), children(int)

Raises:

TypeError – When tagid is not an integer

GetTargetTags(target, targetid, tagclass=None)[source]

Returns a list of all tags of a target. A target can be a song (target = "song") an album (target = "album") or a video (target = "video"). This list contains all classes of tags if tagclass is None, otherwise only of type tagclass.

The returned list is the target-tag-mapping augmented with the tag-entry. So, each element in the list is a merged dictionary of the table row of the mapping and the tag itself. The id entry in the dictionary is the ID of the Tag and identical to the entry tagid. The ID of the ID of the entry in the mapping-table is entryid.

Parameters:
  • target (str) – Target that shall be tagged ("song", "album" or "video")

  • targetid (int) – ID of the target that tags shall be returned (song, album or video ID)

  • tagclass (int) – If not None only tags of a specific class will be returned

Returns:

A list of tags or an empty list if there are no tags

Raises:
  • TypeError – If targetid is None

  • ValueError – If tagclass is set to an invalid value (None is valid)

  • ValueError – If target not in {“song”, “album”, “video”}

Example

tags = database.GetTargetTags("song", songid)
for tag in tags:
    print("Tagname: %s",  tag["name"], end="; ")
    print("Approval: %i", tag["approval"])
    print("Approval: %f", tag["confidence"])
GetVideoById(videoid)[source]

Returns an video entry if available

Parameters:

videoid – entry ID of the video in the video table

Returns:

An video entry or None it the video does not exits

Raises:
  • TypeError – If videoid is not set

  • AssertionError – If there is more than one video with the given ID

GetVideoByPath(path)[source]

Returns a video from the database that matches the path

Parameters:

path (str) – A video path relative to the music root directory

Returns:

A MusicDB Video dictionary or None if there is no video with that path

Raises:
  • TypeError – If path is None

  • AssertionError – If there is more than one video with the same path

GetVideos()[source]

This method returns an unsorted list with all videos.

Example

The following example prints all videos

albums = musicdb.GetVideos()
for video in videos:
    print(video["name"])
Returns:

A list with all videos in the database.

GetVideosByArtistId(artistid)[source]

This method returns an unsorted list with all videos of an artist.

Example

The following example prints all videos of the artist with the ID 1000

albums = musicdb.GetVideosByArtistId(artistid = 1000)
for video in videos:
    print(video["name"])
Parameters:

artistid – ID for an artist whose videos shall be returned.

Returns:

A list with all videos of an artist.

ModifyTag(tagname, tagclass, columnname, newvalue)[source]

This method allows to modify most of the attributes of a tag. The tagname and tagclass addresses the tag, columnname the attribute. newvalue is the new attribute set for the tag.

In case the icon gets modified, take care that the icon type is up to date. (update order does not matter).

For colors, None is a valid type to remove color

Parameters:
  • tagname (str) – Name of the tag that shall be modified

  • tagclass (int) – Class of the tag

  • columnname (str) – The name of the attribute that shall be modified

  • newvalue – The new value. Read the introduction at the top of the document to see what values are possible for a specific attribute

Returns:

None

Raises:
  • TypeError – if tagname is not a string or parentid does not have the value it should have regarding the specification

  • TypeError – When color is not a string and not None

  • ValueError – When tagclass has an invalid value

  • ValueError – If columnname is not “name”, “parentid”, “icontype”, “icon”, “color”, “posx”, “posy”

  • ValueError – If columnname is “color” and newvalue is not a valid #RRGGBB-Formated string

  • ValueError – If columnname is “icontype” and newvalue is not valid

ModifyTagById(tagid, columnname, newvalue)[source]

This method allows to modify most of the attributes of a tag. The tagid addresses the tag, columnname the attribute. newvalue is the new attribute set for the tag.

In case the icon gets modified, take care that the icon type is up to date. (update order does not matter).

For colors, None is a valid type to remove color

Parameters:
  • tagid (int) – ID of the tag to modify

  • columnname (str) – The name of the attribute that shall be modified

  • newvalue – The new value. Read the introduction at the top of the document to see what values are possible for a specific attribute

Returns:

None

Raises:
  • TypeError – if tagid is not an integer

  • TypeError – When color is not a string and not None

  • ValueError – If columnname is not “name”, “parentid”, “icontype”, “icon”, “color”, “posx”, “posy”

  • ValueError – If columnname is “color” and newvalue is not a valid #RRGGBB-Formated string

  • ValueError – If columnname is “icontype” and newvalue is not valid

RemoveAlbum(albumid)[source]

This method removes an album entry and all related data from all tables.

The removed data are:

  • The complete row in the album-table for this album

  • All tags of this album (not the tag definition)

Parameters:

albumid (int) – ID of the album

Returns:

None

Raises:

TypeError – When albumid is not an integer or string

RemoveArtist(artistid)[source]

This method removes an artist entry and all related data from all tables.

The removed data are:

  • The complete row in the artist-table for this artist

Parameters:

artistid (int) – ID of the artist

Returns:

None

Raises:

TypeError – When artistid is not an integer or string

RemoveSong(songid)[source]

This method removes a song entry and all related data from all tables.

The removed data are:

  • The complete row in the songs-table for this song

  • The lyrics of this song

  • All tags of this song (not the tag definition)

  • Decrementation of the albums numofsongs value. (not the numofcds entry!)

Parameters:

songid (int) – ID of the song

Returns:

None

Raises:

TypeError – When songid is not an integer or string

RemoveTargetTag(target, targetid, tagid)[source]

Removes an association between a target and a tag in the tag map. In short: Removes a tag from a song, a video or an album.

Parameters:
  • target (str) – Target that shall be tagged ("song" for a song, "video" for a video, "album" for an album)

  • targetid (int) – ID of the target that shall be tagged. (a song ID, video ID or an album ID)

  • tagid (int) – ID of the tag that shall be associated with the target

Returns:

None

Raises:
  • ValueError – If target not in {"song", "video", "album"}

  • TypeError – If songid == None or tagid == None

SetAlbumAddedTime(albumid, added)[source]

This method updates the entry of an album that stores the date and time when the album has been added. So this is the time the album has been imported into the MusicDB universe.

The time must be a unix time stamp in seconds.

Usually this time gets set by the import routines.

Parameters:
  • albumid (int) – ID of the album

  • added (int) – The time the album has been added

Returns:

None

Raises:

TypeError – If albumid is not an integer and added not a int

SetAlbumHiddenState(albumid, hiddenstate)[source]

Hides or shows an album depending on the hide state. When hidden == True the album gets hidden, when hidden == False the hidden state gets reset to make the album visible again.

Parameters:
  • albumid (int) – ID of the album

  • hidden (bool) – Hide or Show the album

Returns:

None

Raises:

TypeError – If albumid is not an integer and hiddenstate not a bool

SetAlbumOrigin(albumid, origin)[source]

This method updates the origin entry of an album. The origin defines where the album has been bought.

Parameters:
  • albumid (int) – ID of the album

  • origin (str) – Defines the origin

Returns:

None

Raises:

TypeError – If albumid is not an integer and origin not a str

SetArtwork(albumid, artworkpath)[source]

This method updates the artworkpath entry of the MusicDB Database for an album.

Parameters:
  • albumid – ID of the album that artwork path shall be updated

  • artworkpath (str) – New relative artwork path for the album

Returns:

None

Raises:
  • TypeError – When albumid is not an integer or a string

  • TypeError – If artworkpath is not of type str

SetArtworkColorByAlbumId(albumid, colorname, color)[source]

This method is for setting a color for an album. Valid color names are the following and must be given as string to the colorname parameter.

  • "bgcolor" - Background color

  • "fgcolor" - Primary foreground color

  • "hlcolor" - Secondary foreground color

The color itself must be in HTML-Format: #RRGGBB.

Parameters:
  • albumid – The ID of the album that color shall be set

  • colorname (str) – Name of the color that shall be set

  • color (str) – Color in HTML format

Returns:

None

Raises:
  • TypeError – If one of the arguments is None

  • ValueError – If colorname not "bgcolor", "fgcolor" or "hlcolor"

  • ValueError – If color length is not 7 and first character not "#"

SetColorThemeByVideoId(videoid, colorname, color)[source]

This method is for setting a color for a video. Valid color names are the following and must be given as string to the colorname parameter.

  • "bgcolor" - Background color

  • "fgcolor" - Primary foreground color

  • "hlcolor" - Secondary foreground color

The color itself must be in HTML-Format: #RRGGBB.

Parameters:
  • videoid – The ID of the video that color shall be set

  • colorname (str) – Name of the color that shall be set

  • color (str) – Color in HTML format

Returns:

None

Raises:
  • TypeError – If one of the arguments is None

  • ValueError – If colorname not "bgcolor", "fgcolor" or "hlcolor"

  • ValueError – If color length is not 7 and first character not "#"

SetLyrics(songid, lyrics, lyricsstate=3)[source]

This method can be used to store or to update lyrics of a song. It stores the lyrics in the lyrics table and updates the lyrics state in the songs table for a given song.

If there are no lyrics for the song, or lyrics shall be removed, the lyrics argument must be None or "". In this case the lyrics state gets forced to SONG_LYRICSSTATE_EMPTY. Only excepetion is, when the lyricsstate is SONG_LYRICSSTATE_NONE which indicates that the song does not have lyrics at all. For example, instrumental songs or intros.

Parameters:
  • songid (int) – ID of the song the lyrics belong to

  • lyrics (str) – The lyrics to store

  • lyricsstate (int) – The new state of the lyrics. Default is “From User” (SONG_LYRICSSTATE_FROMUSER)

Returns:

Always True

Raises:
  • TypeError – When sonid is not an integer or string

  • TypeError – If lyrics state is not a number.

  • ValueError – If lyrics state is not in SONG_LYRICSSTATE_*

SetTargetTag(target, targetid, tagid, approval=1, confidence=None)[source]

This method sets a tag for a target. A target can be a song (target = "song"), a video (target = "video") or an album (target = "album").

The defaults for this method assume that the tag got set by a user.

  • If approval equals 1 or 2, the confidence gets set to 1.0.

  • If approval equals 0 a confidence must be given, otherwise an AssertionError gets thrown.

If the tag was already set, the approval and confidence values get updated. But only if the new approval level is greater or equal to the already set one.

Parameters:
  • target (str) – Target that shall be tagged ("song" for a song, "video" for a video, "album" for an album)

  • targetid (int) – ID of the target that shall be tagged. (a song ID, videoid or an album ID)

  • tagid (int) – ID of the tag that shall be associated with the target

  • approval (int) – Approval of the association. Default is 1 - “Set by User”

  • confidence (float) – Confidence of the association in case approval is 0 - “Set by AI”

Returns:

None

Raises:
  • ValueError – If target not in {"song", "album", "video"}

  • TypeError – If approval == 0 and confidence == None

  • ValueError – If approval not in {0,1,2}

  • ValueError – If targetid == None or tagid == None

  • AssertionError – If there already exists more than one entry

  • ValueError – When there is no tag existing with the given tagid

SetVideoFrames(videoid, framesdirectory=None, thumbnailfile=None, previewfile=None)[source]

This method updates the frames directory, thumbnail file and preview file entry in the database for a video with the ID videoid.

The files and directory can be None. In this case the values will not be changed. The video ID must be a valid ID of a video existing in the database.

Parameters:
  • videoid (int) – ID of the video that database entry shall be updated

  • framesdirectory (str, NoneType) – Path of the video specific sub directory containing all frames/preview files. Relative to the video frames root directory

  • thumbnailfile (str, NoneType) – File name of the frame that shall be used as thumbnail, relative to framesdir

  • previewfile (str, NoneType) – File name of the preview animation, relative to framesdir

Returns:

True on success, otherwise False

Raises:

TypeError – when the types of the arguments mismatch

SetVideoTimeFrame(videoid, begin, end)[source]

Set the time frame for a video. This time frame defines where the player should start playing the video and where it should end. The values are floating point numbers an represent the second inside the video file.

Parameters:
  • videoid (int) – ID of the video

  • begin (int) – Begin of the main content in seconds.

  • end (int) – End of the main content in seconds.

Returns:

True on success, otherwise false

Raises:
  • TypeError – If begin or end if not int

  • ValueError – If begin > end

SplitTagsByClass(tags)[source]

Splits a list of tags into several lists, each of a specific class.

If the tags parameter is None, this method returns [] for each class.

Parameters:

tags (list) – A list of tags

Returns:

genres, subgenres, moods

Return type:

three lists, each of a specific class

Raises:

ValueError – If a tag contains an invalid class ID

Exampe:

tags = database.GetTagretTags("song", songid)
genres, subgenres, moods = database.SplitTagsByClass(tags)
UpdateMusicProperty(musicid, stat, value, musictype)[source]

This method updates a songs or videos property and statistic, depending on the value of musictype.

Statistics are:

  • Statistics: "likes", "dislikes", "lastplayed"

  • Properties: "favorite", "disabled", "liverecording", "badaudio", "lyricsvideo" (for videos only)

Possible values are:

  • "inc", "love", "yes": Increment value or set to 1 for boolean properties

  • "dec", "hate": Decrement value

  • "reset", "none", "no": Set value to 0

favorite can have three states:

  • -1: Hated song

  • 0: Normal song

  • 1: Loved song

likes and dislikes can be incremented and decremented.

lastplayed expects the unix time as integer given as value.

Parameters:
  • musicid (int) – ID of the song or video

  • stat (str) – Name of the statistics to update

  • value (str/int) – How to update

  • musictype (str) – "song" or "video"

Returns:

None

Raises:
  • TypeError – When songid is not an integer or string

  • ValueError – if stats or value have an invalid value. Deprecated statistics do not raise an exception.

  • TypeError – When stat == "lastplayed" but value is not an integer

  • ValueError – When an expected unix time is less than 0

  • ValueError – When musictype is not "song" or "video"

  • ValueError – For an unknown property or statistic

UpdateSongStatistic(songid, stat, value)[source]

Alias to UpdateMusicProperty() with last parameter musictype = "song".

UpdateVideoStatistic(videoid, stat, value)[source]

Alias to UpdateMusicProperty() with last parameter musictype = "video".

WriteAlbum(album)[source]

Updates the whole row for an album.

WriteArtist(artist)[source]

Updates the whole row for an artist.

WriteSong(song)[source]

Updates the whole row for a song.

Parameters:

song – A dictionary representing a whole row in the songs table

Returns:

None

WriteTag(tag)[source]

Updates the whole row for a tag.

WriteVideo(video)[source]

Updates the whole row for a video.

Parameters:

video – A dictionary representing a whole row in the videos table

Returns:

None