mirror of
https://github.com/beetbox/beets.git
synced 2025-12-06 08:39:17 +01:00
225 lines
8.4 KiB
ReStructuredText
225 lines
8.4 KiB
ReStructuredText
LastGenre Plugin
|
|
================
|
|
|
|
The ``lastgenre`` plugin fetches *tags* from `Last.fm`_ and assigns them as
|
|
genres to your albums and items.
|
|
|
|
.. _Last.fm: https://last.fm/
|
|
|
|
Installation
|
|
------------
|
|
|
|
To use the ``lastgenre`` plugin, first enable it in your configuration (see
|
|
:ref:`using-plugins`). Then, install ``beets`` with ``lastgenre`` extra
|
|
|
|
.. code-block:: bash
|
|
|
|
pip install "beets[lastgenre]"
|
|
|
|
Usage
|
|
-----
|
|
|
|
The plugin chooses genres based on a *whitelist*, meaning that only certain
|
|
tags can be considered genres. This way, tags like "my favorite music" or "seen
|
|
live" won't be considered genres. The plugin ships with a fairly extensive
|
|
`internal whitelist`_, but you can set your own in the config file using the
|
|
``whitelist`` configuration value or forgo a whitelist altogether by setting
|
|
the option to ``no``.
|
|
|
|
The genre list file should contain one genre per line. Blank lines are ignored.
|
|
For the curious, the default genre list is generated by a `script that scrapes
|
|
Wikipedia`_.
|
|
|
|
.. _script that scrapes Wikipedia: https://gist.github.com/1241307
|
|
.. _internal whitelist: https://raw.githubusercontent.com/beetbox/beets/master/beetsplug/lastgenre/genres.txt
|
|
|
|
Canonicalization
|
|
^^^^^^^^^^^^^^^^
|
|
|
|
The plugin can also *canonicalize* genres, meaning that more obscure genres can
|
|
be turned into coarser-grained ones that are present in the whitelist. This
|
|
works using a `tree of nested genre names`_, represented using `YAML`_, where
|
|
the leaves of the tree represent the most specific genres.
|
|
|
|
The most common way to use this would be with a custom whitelist containing only
|
|
a desired subset of genres. Consider for a example this minimal whitelist::
|
|
|
|
rock
|
|
heavy metal
|
|
pop
|
|
|
|
together with the default genre tree. Then an item that has its genre specified
|
|
as *viking metal* would actually be tagged as *heavy metal* because neither
|
|
*viking metal* nor its parent *black metal* are in the whitelist. It always
|
|
tries to use the most specific genre that's available in the whitelist.
|
|
|
|
The relevant subtree path in the default tree looks like this::
|
|
|
|
- rock:
|
|
- heavy metal:
|
|
- black metal:
|
|
- viking metal
|
|
|
|
Considering that, it's not very useful to use the default whitelist (which
|
|
contains about any genre contained in the tree) with canonicalization because
|
|
nothing would ever be matched to a more generic node since all the specific
|
|
subgenres are in the whitelist to begin with.
|
|
|
|
|
|
.. _YAML: https://yaml.org/
|
|
.. _tree of nested genre names: https://raw.githubusercontent.com/beetbox/beets/master/beetsplug/lastgenre/genres-tree.yaml
|
|
|
|
|
|
Genre Source
|
|
^^^^^^^^^^^^
|
|
|
|
When looking up genres for albums or individual tracks, you can choose whether
|
|
to use Last.fm tags on the album, the artist, or the track. For example, you
|
|
might want all the albums for a certain artist to carry the same genre.
|
|
The default is "album". When set to "track", the plugin will fetch *both*
|
|
album-level and track-level genres for your music when importing albums.
|
|
|
|
|
|
Multiple Genres
|
|
^^^^^^^^^^^^^^^
|
|
|
|
By default, the plugin chooses the most popular tag on Last.fm as a genre. If
|
|
you prefer to use a *list* of popular genre tags, you can increase the number
|
|
of the ``count`` config option.
|
|
|
|
Lists of up to *count* genres will then be used instead of single genres. The
|
|
genres are separated by commas by default, but you can change this with the
|
|
``separator`` config option.
|
|
|
|
`Last.fm`_ provides a popularity factor, a.k.a. *weight*, for each tag ranging
|
|
from 100 for the most popular tag down to 0 for the least popular.
|
|
The plugin uses this weight to discard unpopular tags. The default is to
|
|
ignore tags with a weight less then 10. You can change this by setting
|
|
the ``min_weight`` config option.
|
|
|
|
Specific vs. Popular Genres
|
|
^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
|
|
By default, the plugin sorts genres by popularity. However, you can use the
|
|
``prefer_specific`` option to override this behavior and instead sort genres
|
|
by specificity, as determined by your whitelist and canonicalization tree.
|
|
|
|
For instance, say you have both ``folk`` and ``americana`` in your whitelist
|
|
and canonicalization tree and ``americana`` is a leaf within ``folk``. If
|
|
Last.fm returns both of those tags, lastgenre is going to use the most
|
|
popular, which is often the most generic (in this case ``folk``). By setting
|
|
``prefer_specific`` to true, lastgenre would use ``americana`` instead.
|
|
|
|
Handling pre-populated tags
|
|
^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
|
|
The ``force``, ``keep_existing`` and ``whitelist`` options control how
|
|
pre-existing genres are handled.
|
|
|
|
As you would assume, setting ``force: no`` **won't touch pre-existing genre
|
|
tags** and will only **fetch new genres for empty tags**. When ``force`` is
|
|
``yes`` the setting of the ``whitelist`` option (as documented in `Usage`_)
|
|
applies to any existing or newly fetched genres.
|
|
|
|
The follwing configurations are possible:
|
|
|
|
**Setup 1** (default)
|
|
|
|
Add new last.fm genres when **empty**. Any present tags stay **untouched**.
|
|
|
|
.. code-block:: yaml
|
|
|
|
force: no
|
|
keep_existing: no
|
|
|
|
**Setup 2**
|
|
|
|
**Overwrite all**. Only fresh last.fm genres remain.
|
|
|
|
.. code-block:: yaml
|
|
|
|
force: yes
|
|
keep_existing: no
|
|
|
|
**Setup 3**
|
|
|
|
**Combine** genres in present tags with new ones (be aware of that with an
|
|
enabled ``whitelist`` setting, of course some genres might get cleaned up. To
|
|
make sure any existing genres remain, set ``whitelist: no``).
|
|
|
|
.. code-block:: yaml
|
|
|
|
force: yes
|
|
keep_existing: yes
|
|
|
|
.. attention::
|
|
If ``force`` is disabled the ``keep_existing`` option is simply ignored
|
|
(since ``force: no`` means ``not touching`` existing tags anyway).
|
|
|
|
|
|
|
|
Configuration
|
|
-------------
|
|
|
|
To configure the plugin, make a ``lastgenre:`` section in your
|
|
configuration file. The available options are:
|
|
|
|
- **auto**: Fetch genres automatically during import.
|
|
Default: ``yes``.
|
|
- **canonical**: Use a canonicalization tree. Setting this to ``yes`` will use
|
|
a built-in tree. You can also set it to a path, like the ``whitelist``
|
|
config value, to use your own tree.
|
|
Default: ``no`` (disabled).
|
|
- **count**: Number of genres to fetch.
|
|
Default: 1
|
|
- **fallback**: A string to use as a fallback genre when no genre is found
|
|
``or`` the original genre is not desired to be kept (``keep_existing: no``).
|
|
You can use the empty string ``''`` to reset the genre.
|
|
Default: None.
|
|
- **force**: By default, lastgenre will fetch new genres for empty tags only,
|
|
enable this option to always try to fetch new last.fm genres. Enable the
|
|
``keep_existing`` option to combine existing and new genres. (see `Handling
|
|
pre-populated tags`_).
|
|
Default: ``no``.
|
|
- **keep_existing**: This option alters the ``force`` behavior.
|
|
If both ``force`` and ``keep_existing`` are enabled, existing genres are
|
|
combined with new ones. Depending on the ``whitelist`` setting, existing and
|
|
new genres are filtered accordingly. To ensure only fresh last.fm genres,
|
|
disable this option. (see `Handling pre-populated tags`_)
|
|
Default: ``no``.
|
|
- **min_weight**: Minimum popularity factor below which genres are discarded.
|
|
Default: 10.
|
|
- **prefer_specific**: Sort genres by the most to least specific, rather than
|
|
most to least popular. Note that this option requires a ``canonical`` tree,
|
|
and if not configured it will automatically enable and use the built-in tree.
|
|
Default: ``no``.
|
|
- **source**: Which entity to look up in Last.fm. Can be
|
|
either ``artist``, ``album`` or ``track``.
|
|
Default: ``album``.
|
|
- **separator**: A separator for multiple genres.
|
|
Default: ``', '``.
|
|
- **whitelist**: The filename of a custom genre list, ``yes`` to use
|
|
the internal whitelist, or ``no`` to consider all genres valid.
|
|
Default: ``yes``.
|
|
- **title_case**: Convert the new tags to TitleCase before saving.
|
|
Default: ``yes``.
|
|
- **extended_debug**: Add additional debug logging messages that show what
|
|
last.fm tags were fetched for tracks, albums and artists. This is done before
|
|
any canonicalization and whitelist filtering is applied. It's useful for
|
|
tuning the plugin's settings and understanding how it works, but it can be
|
|
quite verbose.
|
|
Default: ``no``.
|
|
|
|
Running Manually
|
|
----------------
|
|
|
|
In addition to running automatically on import, the plugin can also be run
|
|
manually from the command line. Use the command ``beet lastgenre [QUERY]`` to
|
|
fetch genres for albums or items matching a certain query.
|
|
|
|
By default, ``beet lastgenre`` matches albums. To match
|
|
individual tracks or singletons, use the ``-A`` switch:
|
|
``beet lastgenre -A [QUERY]``.
|
|
|
|
To disable automatic genre fetching on import, set the ``auto`` config option
|
|
to false.
|