Music tagging process

Beets

Install

Current Debian versions tend to be old.

python3.7 -m venv venv37
source venv37/bin/activate
pip install -U beets

Import

  1. Check the config for albumartist vs album
  2. beet import /path/to/downloaded/album

Move

  1. Tweak settings in ~/.config/beets/config.yaml
  2. beet move -a [-p] album-name

MusicBrainz

  1. picard
    1. Import
    2. Collect
    3. Scan
  2. easytag
    1. write playlists
    2. check CRLF (should have DOS line-endings)

Picard Settings

Metadata

Translate artist names to locale : ON, English (fixes Kitaro)

Use standardised artist names : ON

Convert Unicode punctuation characters to ASCII : ON

Use release relationships : ON

Use track relationships : ON

Use folksonomy tags as genre : ON

Preferred Release Countries : UK, US, ZA

Preferred Release Formats : CD

Before Tagging : clear existing, remove ID3 from FLAC, remove APE from MP3

Tag Compatibility : ID3v2.4, UTF-8

Albums

Cover Art : Save cover images as separate files, folder

Collections

Cover Art : Embed cover images into tags, Embed only front images

File naming

Replace non-ASCII characters : OFF

Replace Windows-incompatible characters : OFF

Delete empty directories : ON

Move additional files : *.jpg *.png

Picard Genres

Plugins : Last.fm.Plus

General Options / Join Tags With : blank

Forces multiple genres into separate tags.

Picard Rename

Default

$if2(%albumartist%,%artist%)/%album%/%artist% - %title%

With Custom Replacements

  • Also replace ' / ' (which is forced to '_' by picard) to '; '
  • Album: drop everything from the second ':' onwards
  • DiscSubtitle: add to the path if it exists

    $replace($noop(?) $replace($noop(:) $replace($noop(") $replace($noop(|) $replace($noop(<) $replace($noop(>) $rreplace(

    $if2(%albumartist%,%artist%)/$if2($rsearch(%album%,(.:.):),%album%)/%discsubtitle%/%artist% - %title%

    ,\s_\b,;) ,>,)) ,<,() ,|,) ,",') ,:, -) ,?,)

Classical

Trying for something like composer/work/performance/(01x01 - )composer - title.

  1. If albumartist has ';' use just the first part (the composer)
  2. In album
    1. If < 30 chars, use it, otherwise
    2. Drop anything from the second ':', or
    3. Drop anything from a '(' onwards
  3. Extract performers from the second part of albumartist
  4. Extract "orchestra, conductor" as best we can
  5. Use discsubtitle (large collections) else:
    1. performer part of the albumartist if it's shorter than 60 chars, else
    2. "orchestra - conductor"
  6. 01x01 if total discs is large (>2)

    $set(_maincomposer,$if2($rsearch(%albumartist%,(.); ),%albumartist%,%artist%)) $set(_work,$if2($if($lt($len(%album%),30),%album%),$rsearch(%album%,(.:.):),$rsearch(%album%,(.)[(]),%album%)) $set(_performers,$rsearch(%albumartist%,; (.))) $set(_conductor,$if2($rsearch(%conductor%,(.);),%conductor%,$rsearch($performer(conductor),(.*);),$performer(conductor))) $set(_orchestra_conductor,$if(%_conductor%,$performer(orchestra)\, %_conductor%,$performer(orchestra))) $set(_performance,$if2(%discsubtitle%,$if($lt($len(%_performers%),60),%_performers%),%_orchestra_conductor%)) $set(_tracknums,$if($gt(%totaldiscs%,2),$num(%discnumber%,2)x$num(%tracknumber%,2) - ))

    %_maincomposer%/%_work%/%_performance%/%_tracknums%%artist% - %title%

Produces:

  • Wolfgang Amadeus Mozart/Don Giovanni/Freiburger Barockorchester, René Jacobs/01x01 - Wolfgang Amadeus Mozart - Il dissoluto punito, ossia il Don Giovanni, K. 527 - Ouverture. Andante - allegro molto.mp3
  • @@Wolfgang Amadeus Mozart/Requiem/Berliner Philharmoniker/Wolfgang Amadeus Mozart - Requiem in D minor, K. 626 (Süßmayr completion) - IIIa. Sequenz - 'Dies irae'.mp3

@@

  • John Rutter/Requiem and other Sacred Music/Choir of Clare College, Cambridge, Timothy Brown/John Rutter - Requiem - I. Requiem Aeternam.ogg

Large Collections

Add 01x01 only if totaldiscs > 1.

album-artist/album/01x01 - artist - title:

$if2(%albumartist%,%artist%)/%album%/$if($gt(%totaldiscs%,1),$num(%discnumber%,2)x$num(%tracknumber%,2) - )%artist% - %title%

Putting it all Together

$set(_maincomposer,$if2($rsearch(%albumartist%,\(.*\); ),%albumartist%,%artist%))
$set(_work,$if2($if($lt($len(%album%),30),%album%),$rsearch(%album%,\(.*:.*\):),$rsearch(%album%,\(.*\)[\(]),%album%))
$set(_performers,$rsearch(%albumartist%,; \(.*\)))
$set(_conductor,$if2($rsearch(%conductor%,\(.*\);),%conductor%,$rsearch($performer(conductor),\(.*\);),$performer(conductor)))
$set(_orchestra_conductor,$if(%_conductor%,$performer(orchestra)\, %_conductor%,$performer(orchestra)))
$set(_performance,$if2(%discsubtitle%,$if($lt($len(%_performers%),60),%_performers%),%_orchestra_conductor%))
$set(_tracknums,$if($gt(%totaldiscs%,2),$num(%discnumber%,2)x$num(%tracknumber%,2) - ))
$replace($noop(.)
$replace($noop(?)
$replace($noop(:)
$replace($noop(")
$replace($noop(|)
$replace($noop(<)
$replace($noop(>)
$rreplace(
$rreplace(
%_maincomposer%/%_work%/%_performance%/%_tracknums%%artist% - %title%
,\\s_\\b,;)
,_, )
,>,\))
,<,\()
,|,)
,",')
,:, -)
,?,)
,...,)