Repository for neat file name string patterns and tagger script snippets

picard
taggerscript
examples
Tags: #<Tag:0x00007f0765853090> #<Tag:0x00007f0765852f50> #<Tag:0x00007f0765852e10>

#7

EDIT 2016-11-02: Updated to version 0.0.4α. Also, if anyone uses Notepad++, I have a fairly good definition of the Picard Tagger Script language, posted below.


Here’s my first attempt at a naming script. You just maybe might be able to guess that I’m a software professional. :wink: But I’m new to this level of detail in this language. (I don’t even know what the language is called or where it’s documented, although I’ve specified file and folder names with it in other tagging apps.)

I want to learn how to create functions to get rid of all the repeated code and to create my own unique functions. And if there’s documentation beyond the Scripting page on the Picard site I’d love to know where it is.

Anyway, if you see anything you like or you think could be improved, don’t hesitate to comment.

Pardon the formatting - it’s copied from the text editor I’m using, with tabs replaced by spaces for display here. This was written for Picard v1.3.2, my first Picard. No guarantees that it works with earlier versions.

$noop(MusicBrainz Picard file naming script.

   Author: Michael Piz [Your intrepid author {YIA}; @Piz on MusicBrainz]
   Version 0.0.4α [2016-11-01, edit history at end]

   Copyright 2016 by Michael Pizolato. This work is licensed under a Creative
   Commons Attribution-NonCommercial-ShareAlike 4.0 International License.
   Details are available at http://creativecommons.org/licenses/by-nc-sa/4.0/
   
   THIS IS AN ALPHA RELEASE!
   USE AT YOUR OWN RISK!

   YIA has a very specific naming convention for files and folders because, 
   while he's a genial fellow, he does have minor OCD tendencies. Here's what 
   this script generates for the examples in Picard's options [as of v1.3.2; 
   the line breaks are for display formatting only]: 
   
   ROOT/Beatles, The/Help! [soundtrack]/Beatles, The • Help! [soundtrack] • 
   07 · Ticket to Ride.mp3

   ROOT/Various Artists/Coup d'État, Volume 1 - Ku De 
   Ta - Prologue/Snowboy · Various Artists • Coup d'État, Volume 1 - Ku De 
   Ta - Prologue • 02.05 · I've Got to Learn the Mambo.mp3 

   Here are some from YIA's own library:

   ROOT/Wings/Wings over America/Wings • Wings over America • 02.11 · Band on 
   the Run [live].mp3 
   
   ROOT/Saint-Saëns, Camille/Saint-Saëns - Piano Concertos 1-5; Wedding Cake 
   Caprice-Valse/Saint-Saëns, Camille • Saint-Saëns - Piano Concertos 1-5; 
   Wedding Cake Caprice-Valse • 02.08 · 'Africa' Fantaisie, Op. 89
   
   Broken down, they look like this:

   ARTIST FOLDER: Beatles, The
    ALBUM FOLDER: Help! [soundtrack]
      TRACK FILE: Beatles, The • Help! [soundtrack] • Track 07 · Ticket to 
                  Ride.mp3

   ARTIST FOLDER: Various Artists
    ALBUM FOLDER: Coup d'État, Volume 1 - Ku De Ta - Prologue
      TRACK FILE: Snowboy · Various Artists • Coup d'État, Volume 1 - Ku De
                  Ta - Prologue • Disc 02 · Track 05 · I've Got to Learn the
                  Mambo.mp3

   ARTIST FOLDER: Wings
    ALBUM FOLDER: Wings over America
      TRACK FILE: Wings • Wings over America • 02.11 · Band on the Run [live]

   ARTIST FOLDER: Saint-Saëns, Camille
    ALBUM FOLDER: Saint-Saëns - Piano Concertos 1-5; Wedding Cake Caprice-Valse
      TRACK FILE: Saint-Saëns, Camille • Saint-Saëns - Piano Concertos 1-5; 
                  Wedding Cake Caprice-Valse • 02.08 · 'Africa' Fantaisie, Op. 
                  89.mp3

   Track filenames duplicate all the folder information because in most UI 
   file search r only the filename of a match is displayed. This way, 
   all the infomation will be in the search results, resulting in unique 
   matches. YIA tends to be impatient, especially with looking things up more 
   than once.

   Here are examples of artist folders:
   
   [Various Artists]
   [unknown artist]
   10,000 Maniacs
   Beatles, The
   Davis, Sammy, Jr
   
   In addition to individual album folders within those, there can be 
   "[unknown album]" and "[singles]" folders. Within any of these, individual 
   track files are stored. In the "[Various Artists]" folder there are 
   individual album folders [and possibly "[unknown album]"]. Track names in 
   the "[Various Artists]" album folders include the form "Artist · Various 
   Artists" so the individual artist is included. Tracks missing a title have 
   "unknown title" assigned as the title. Thus, should all fail, the 
   following is possible [though somewhat unlikely]:
   
   [unknown artist]/[unknown album]/[unknown artist] • [unknown album] • 
   [unknown title].mp3
   
   The brackets are added so those folders sort to the top of an ascending 
   alphabetical list [in Windows, anyway] instead of being mixed in with the  
   individual artist or album folders.
   
   Final note: You may wonder why YIA has created all these verbose constants 
   instead of just using their [shorter, duh] corresponding characters or 
   strings. That's because he doesn't trust himself not to drop extraneous 
   characters in this language. This language works by building a string from 
   the results of all the functions used plus, importantly, any explicit 
   characters in the script. For example, if you put "xyzzy" at the end of 
   your script, just literally like that, whatever final string you generate 
   will end in "xyzzy" even though it's not generated by a function call, and 
   no error will be displayed because that's how the language works. [If you 
   are insane and want to name all your files "foobar", your script can 
   consist solely of that string.] Stray spaces or punctuation or whatnot 
   strewn hither and yon could affect the final string in very difficult to 
   debug ways. Therefore, YIA, being completely untrusting of himself in such 
   matters, doesn't allow himself the possibility of strays. By using 
   variables as constants and never including whitespace in function calls 
   [except at the beginning of lines, where it is ignored], the possibility of 
   stray character gremlins is all but eliminated. [In addition, using 
   "_kNull" makes it explicit where null strings are used, also making 
   debugging, and reading the code, easier.]
   )

$noop(Basic constants.)
   $set(_kNull,)
   $set(_kSpace, )
   $set(_kComma,\,)
   $set(_kSingleQuote,')
   $set(_kEllipsis,…)
   $set(_kPeriod,.)
   $set(_kAmpersand, & )
   $set(_kNoteBracketLeft,[)
   $set(_kNoteBracketRight,])
$noop(End basic constants.)

$noop(Aticles.)
   $set(_kA,A)
   $set(_kAn,An)
   $set(_kThe,The)
$noop(End articles.)

$noop(Folder and track name constants.)
   $set(_kFolderSep,/)
   $noop(
      There are three levels of separators within track names. The top levels 
      are "Artist • Album • Track", corresponding to "Artist/Album/Track" in 
      the file system. In track names, for example when the album artist is 
      "Various Artists", one of the possible second levels is "Artist · 
      Various Artists" [see the Snowboy and Saint-Saëns examples above; also 
      note that the first and second level separators are different 
      characters, i.e. U+2022: Bullet and U+00B7: Middle Dot; the third level 
      separartor is U+002D: Hyphen-Minus, the simple minus sign]. The third 
      level separator replaces any characters in artist/album/track names that 
      are illegal filename characters, e.g. "Some Band: Greatest Hits" becomes 
      "Some Band - Greatest Hits" [again, see the Snowboy and Saint-Saëns 
      examples].
      )
      $set(_kTrackSep1, • )
      $set(_kTrackSep2, · )
      $set(_kTrackSep3, - )
$noop(End folder and track name constants.)

$noop(Filename substitution regex constants.)
   $noop(All bracket types.)
      $set(_kReOpenBrackets,[\\%_kNoteBracketLeft%\({])
      $set(_kReCloseBrackets,[\\%_kNoteBracketRight%\){])
   $noop(For replacing three consecutive periods with one ellipsis.)
      $set(_kRe3Dots,\\%_kPeriod%\\%_kPeriod%\\%_kPeriod%)
   $noop(Trim all multiple spaces down to single spaces.)
      $set(_kMultiSpace,\\s+)
   $noop(
      Remove characters not permitted in file or folder names. These are
      treated as separators and replaced with _kTrackSep2. Underscore isn't
      really an illegal char but having it here gets it replaced by a
      separator.
      )
      $set(_kReIllegalFileChars,\\s*[/\\><*:_|]+\\s*)
   $noop(
      Replace all quote marks with single quotes. The double quote isn't part
      of the illegal chars because those get dropped, not replaced.
      )
      $set(_kReQuoteMarks,["“”‘’]+)
   $noop(
      Remove question marks entirely. E.g., "What Kind of Fool Am I?" becomes
      "What Kind of Fool Am I". This isn't part of the illegal chars because
      those get dropped, not replaced. The inverted question mark is dropped
      for aesthetic reasons - it won't have its mate.
      )
      $set(_kReQuestionMarks,[¿?]+)
   $noop(
      Windows doesn't allow periods as the final char of folder names. It 
      automatically drops them in Windows Explorer, but YIA doesn't know what 
      happens programatically so it's best to drop them here.
      )
      $set(_kReEndPeriod,\\.\$)
   $noop(Case insensitivity.)
      $set(_kReCaseInsensitive,\(?i\))
   $noop(And. Always replace wth '&'.)
      $set(_kReAnd,%_kReCaseInsensitive%\\sand\\s)
   $noop(
      Remove "feat." or "ft." [with or without the periods] plus everything 
      that follows [and precedes, if inside brackets].
      )
      $set(_kReFeat,
         \\s+\(%_kReOpenBrackets%.*\)?f\(ea\)?t\\.?.*\(%_kReCloseBrackets%.*\)?
         )
$noop(End filename substitution regex constants.)

$noop(Artist/album/title/media/track constants.)
   $noop(
      Release types. Comment shows whether value goes in album or track 
      notes. Album and single determine the others. "Other" isn't used 
      because it provides no information.
      )
      $set(_kAlbum,album)           $noop(N/A)
      $set(_kSingle,single)         $noop(N/A)
      $set(_kEP,ep)                 $noop(album)
      $set(_kBroadcast,broadcast)   $noop(track)
      $set(_kOther,other)           $noop(N/A)
   $noop(
      Secondary release types. Comment shows whether value goes in album 
      or track notes.
      )
      $set(_kCompilation,compilation)  $noop(album)
      $set(_kSoundtrack,soundtrack)    $noop(album)
      $set(_kAudiobook,audiobook)      $noop(album)
      $set(_kMixtape,mixtape/street)   $noop(album)
      $set(_kSpokenword,spokenword)    $noop(track)
      $set(_kInterview,interview)      $noop(track)
      $set(_kLive,live)                $noop(track)
      $set(_kRemix,remix)              $noop(track)
      $set(_kDJMix,dj-mix)             $noop(track)
   $noop(Default artist/album/title.)
      $set(_kUnknownArtist,unknown artist)
      $set(_kUnknownAlbum,unknown album)
      $set(_kNoTitle,unknown title)
   $noop(
      NOTE: The next two must duplicate the "Various artists" and "Non-album
      tracks" option settings. I've submitted a Picard feature request to
      have those options be made available as tags, to avoid having to
      maintain them in two places. That ticket can be found at 
      https://tickets.musicbrainz.org/browse/PICARD-849
      )
      $set(_kVariousArtists,Various Artists)
      $set(_kNonAlbumTracks,%_kNoteBracketLeft%singles%_kNoteBracketRight%)
   $noop(Media and track number.)
      $set(_kDefaultMedia,Disc)
      $set(_kTrackTxt,Track )
$noop(End artist/album/title/media/track constants.)

$noop(Copies of existing tags.

   After this, only the copies are used. In some instances, the tag is later
   replaced by the processed copy.
   )
   $set(_media,%media%)
   $set(_totaldiscs,%totaldiscs%)
   $set(_discNum,%discnumber%)
   $set(_trackNum,%tracknumber%)
   $noop(Album, artist, album artist, and title are more complex.)
      $set(_artist,
         $if2(
            %artistsort%,
            %artist%,
            %albumartistsort%,
            %albumartist%,
            %_kUnknownArtist%
            )
         )
      $set(_albumArtist,
         $noop(albumartistsort already handles "A" and The")
         $swapprefix(
            $if2(%albumartistsort%,
               %albumartist%,
               %artistsort%,
               %artist%,
               %_kUnknownArtist%
               ),
            %_kAn%
            )
         )
      $set(_album,
         $swapprefix(
            $if2(%album%,%_kUnknownAlbum%),
            %_kA%,%_kAn%,%_kThe%
            )
         )
      $set(_title,
         $swapprefix(
            $if2(%title%,%_kNoTitle%),
            %_kA%,%_kAn%,%_kThe%
            )
         )
$noop(End copies of existing tags.)

$noop(Album/artist/track characteristics.)
   $set(_isVariousArtists,$eq(%albumartist%,%_kVariousArtists%))
   $set(_differentAlbumArtist,$ne(%artistsort%,%albumartistsort%))
   $set(_isUnknownArtist,
      $or($not(%albumartist%),$eq(%albumartist%,%_kUnknownArtist%))
      )
   $set(_isUnknownAlbum,
      $or($not(%album%),$eq(%album%,%_kUnknownAlbum%))
      )
   $set(_isSingle,$in(%releasetype%,%_kSingle%))
$noop(End track characteristics.)

$noop(Album/track notes.)
   $set(_relType,%_kSoundtrack%)
   $set(_pattern,
      %_kReCaseInsensitive%\(%_kReOpenBrackets%?%_relType%%_kReCloseBrackets%?\)
      )
   $if($rsearch(%_secondaryreleasetype%,%_pattern%),
      $set(_artist,$rreplace(%_artist%,%_pattern%,%_kNull%))
      $set(_album,$rreplace(%_album%,%_pattern%,%_kNull%))
      $set(_title,$rreplace(%_title%,%_pattern%,%_kNull%))
      $set(_albumNotes,
         %_albumNotes%$if(%_albumNotes%,%_kComma%%_kSpace%)%_relType%
         )
      )
   $set(_relType,%_kAudiobook%)
   $set(_pattern,
      %_kReCaseInsensitive%\(%_kReOpenBrackets%?%_relType%%_kReCloseBrackets%?\)
      )
   $if($rsearch(%_secondaryreleasetype%,%_pattern%),
      $set(_artist,$rreplace(%_artist%,%_pattern%,%_kNull%))
      $set(_album,$rreplace(%_album%,%_pattern%,%_kNull%))
      $set(_title,$rreplace(%_title%,%_pattern%,%_kNull%))
      $set(_albumNotes,
         %_albumNotes%$if(%_albumNotes%,%_kComma%%_kSpace%)%_relType%
         )
      )
   $set(_relType,%_kMixtape%)
   $set(_pattern,
      %_kReCaseInsensitive%\(%_kReOpenBrackets%?%_relType%%_kReCloseBrackets%?\)
      )
   $if($rsearch(%_secondaryreleasetype%,%_pattern%),
      $set(_artist,$rreplace(%_artist%,%_pattern%,%_kNull%))
      $set(_album,$rreplace(%_album%,%_pattern%,%_kNull%))
      $set(_title,$rreplace(%_title%,%_pattern%,%_kNull%))
      $set(_albumNotes,
         %_albumNotes%$if(%_albumNotes%,%_kComma%%_kSpace%)%_relType%
         )
      )
   $set(_relType,%_kCompilation%)
   $set(_pattern,
      %_kReCaseInsensitive%\(%_kReOpenBrackets%?%_relType%%_kReCloseBrackets%?\)
      )
   $if($not(%_isVariousArtists%)
      $if($rsearch(%_secondaryreleasetype%,%_pattern%),
         $set(_artist,$rreplace(%_artist%,%_pattern%,%_kNull%))
         $set(_album,$rreplace(%_album%,%_pattern%,%_kNull%))
         $set(_title,$rreplace(%_title%,%_pattern%,%_kNull%))
         $set(_albumNotes,
            %_albumNotes%$if(%_albumNotes%,%_kComma%%_kSpace%)%_relType%
            )
         ),
      %_kNull%
      )
   $set(_relType,%_kEP%)
   $set(_pattern,
      %_kReCaseInsensitive%\(%_kReOpenBrackets%?%_relType%%_kReCloseBrackets%?\)
      )
   $if($rsearch(%releasetype%,%_pattern%),
      $set(_artist,$rreplace(%_artist%,%_pattern%,%_kNull%))
      $set(_album,$rreplace(%_album%,%_pattern%,%_kNull%))
      $set(_title,$rreplace(%_title%,%_pattern%,%_kNull%))
      $set(_albumNotes,
         %_albumNotes%$if(%_albumNotes%,%_kComma%%_kSpace%)%_relType%
         )
      )
   $set(_relType,%_kLive%)
   $set(_pattern,
      %_kReCaseInsensitive%\(%_kReOpenBrackets%?%_relType%%_kReCloseBrackets%?\)
      )
   $if($rsearch(%_secondaryreleasetype%,%_pattern%),
      $set(_artist,$rreplace(%_artist%,%_pattern%,%_kNull%))
      $set(_album,$rreplace(%_album%,%_pattern%,%_kNull%))
      $set(_title,$rreplace(%_title%,%_pattern%,%_kNull%))
      $set(_trackNotes,
         %_trackNotes%$if(%_trackNotes%,%_kComma%%_kSpace%)%_relType%
         )
      )
   $set(_relType,%_kBroadcast%)
   $set(_pattern,
      %_kReCaseInsensitive%\(%_kReOpenBrackets%?%_relType%%_kReCloseBrackets%?\)
      )
   $if($rsearch(%releasetype%,%_pattern%),
      $set(_artist,$rreplace(%_artist%,%_pattern%,%_kNull%))
      $set(_album,$rreplace(%_album%,%_pattern%,%_kNull%))
      $set(_title,$rreplace(%_title%,%_pattern%,%_kNull%))
      $set(_trackNotes,
         %_trackNotes%$if(%_trackNotes%,%_kComma%%_kSpace%)%_relType%
         ),
      )
   $set(_relType,%_kSpokenword%)
   $set(_pattern,
      %_kReCaseInsensitive%\(%_kReOpenBrackets%?%_relType%%_kReCloseBrackets%?\)
      )
   $if($rsearch(%_secondaryreleasetype%,%_pattern%),
      $set(_artist,$rreplace(%_artist%,%_pattern%,%_kNull%))
      $set(_album,$rreplace(%_album%,%_pattern%,%_kNull%))
      $set(_title,$rreplace(%_title%,%_pattern%,%_kNull%))
      $set(_trackNotes,
         %_trackNotes%$if(%_trackNotes%,%_kComma%%_kSpace%)%_relType%
         )
      )
   $set(_relType,%_kInterview%)
   $set(_pattern,
      %_kReCaseInsensitive%\(%_kReOpenBrackets%?%_relType%%_kReCloseBrackets%?\)
      )
   $if($rsearch(%_secondaryreleasetype%,%_pattern%),
      $set(_artist,$rreplace(%_artist%,%_pattern%,%_kNull%))
      $set(_album,$rreplace(%_album%,%_pattern%,%_kNull%))
      $set(_title,$rreplace(%_title%,%_pattern%,%_kNull%))
      $set(_trackNotes,
         %_trackNotes%$if(%_trackNotes%,%_kComma%%_kSpace%)%_relType%
         )
      )
   $set(_relType,%_kRemix%)
   $set(_pattern,
      %_kReCaseInsensitive%\(%_kReOpenBrackets%?%_relType%%_kReCloseBrackets%?\)
      )
   $if($rsearch(%_secondaryreleasetype%,%_pattern%),
      $set(_artist,$rreplace(%_artist%,%_pattern%,%_kNull%))
      $set(_album,$rreplace(%_album%,%_pattern%,%_kNull%))
      $set(_title,$rreplace(%_title%,%_pattern%,%_kNull%))
      $set(_trackNotes,
         %_trackNotes%$if(%_trackNotes%,%_kComma%%_kSpace%)%_relType%
         )
      )
   $set(_relType,%_kDJMix%)
   $set(_pattern,
      %_kReCaseInsensitive%\(%_kReOpenBrackets%?%_relType%%_kReCloseBrackets%?\)
      )
   $if($rsearch(%_secondaryreleasetype%,%_pattern%),
      $set(_artist,$rreplace(%_artist%,%_pattern%,%_kNull%))
      $set(_album,$rreplace(%_album%,%_pattern%,%_kNull%))
      $set(_title,$rreplace(%_title%,%_pattern%,%_kNull%))
      $set(_trackNotes,
         %_trackNotes%$if(%_trackNotes%,%_kComma%%_kSpace%)%_relType%
         )
      )
   $if(%_albumNotes%,
      $set(_albumNotes,
         %_kSpace%%_kNoteBracketLeft%%_albumNotes%%_kNoteBracketRight%
         )
      )
   $if(%_trackNotes%,
      $set(_trackNotes,
         %_kSpace%%_kNoteBracketLeft%%_trackNotes%%_kNoteBracketRight%
         )
      )
$noop(End album/track notes.)

$noop(Set up file/folder names.)
   $noop(Artist. Only used for the track filename.)
      $set(_artist,$rreplace($rreplace($rreplace($rreplace(%_artist%,
         %_kReFeat%,%_kNull%),
         %_kMultiSpace%,%_kSpace%),
         %_kRe3Dots%,%_kEllipsis%),
         %_kReAnd%,%_kAmpersand%)
         )
      $noop(
         At this point the artist to be used for tagging is "clean", so set
         the actual tag value. Similarly for album artist and album, below.
         )
         $set(artist,%_artist%)
      $noop(Scrub _artist for file names.)
         $set(_artist,$rreplace($rreplace($rreplace(%_artist%,
            %_kReQuestionMarks%,%_kNull%),
            %_kReQuoteMarks%,%_kSingleQuote%),
            %_kReIllegalFileChars%,%_kTrackSep3%)
            )
      $noop(Make the filename part.)
         $set(_artistTrack,
            %_artist%
            $if(%_differentAlbumArtist%,
               %_kTrackSep2%,
               %_kTrackSep1%
               )
            )
   $noop(End artist.)

   $noop(Album artist.)
      $set(_albumArtist,$rreplace($rreplace($rreplace($rreplace(%_albumArtist%,
         %_kReFeat%,%_kNull%),
         %_kMultiSpace%,%_kSpace%),
         %_kRe3Dots%,%_kEllipsis%),
         %_kReAnd%,%_kAmpersand%)
         )
      $set(albumartist,%_albumArtist%)
      $set(_albumArtist,$rreplace($rreplace($rreplace(%_albumArtist%,
         %_kReQuestionMarks%,%_kNull%),
         %_kReQuoteMarks%,%_kSingleQuote%),
         %_kReIllegalFileChars%,%_kTrackSep3%)
         )
      $set(_albumArtist,$rreplace(%_albumArtist%,%_kReEndPeriod%,%_kNull%))
      $if(%_differentAlbumArtist%,
         $noop(_albumArtistTrack is unnecesasry when they match.)
         $set(_albumArtistTrack,
            $if(%_isUnknownArtist%,
               %_kNoteBracketLeft%%_albumArtist%%_kNoteBracketRight%,
               %_albumArtist%
               )
               %_kTrackSep1%
            )
         )
      $set(_albumArtistFolder,
         $if($or(%_isVariousArtists%,%_isUnknownArtist%),
            %_kNoteBracketLeft%%_albumArtist%%_kNoteBracketRight%,
            %_albumArtist%
            )
            %_kFolderSep%
         )
   $noop(End album artist.)

   $noop(Album.)
      $set(_album,$rreplace($rreplace($rreplace($rreplace(%_album%,
         %_kReFeat%,%_kNull%),
         %_kMultiSpace%,%_kSpace%),
         %_kRe3Dots%,%_kEllipsis%),
         %_kReAnd%,%_kAmpersand%)
         )
      $set(_album,%_album%%_albumNotes%)
      $set(album,%_album%)
      $set(_album,$rreplace($rreplace($rreplace(%_album%,
         %_kReQuestionMarks%,%_kNull%),
         %_kReQuoteMarks%,%_kSingleQuote%),
         %_kReIllegalFileChars%,%_kTrackSep3%)
         )
      $set(_album,$rreplace(%_album%,%_kReEndPeriod%,%_kNull%))
      $set(_albumTrack,$if($not(%_isSingle%),%_album%%_kTrackSep1%))
      $set(_albumFolder,
         $if(%_isUnknownAlbum%,
            %_kNoteBracketLeft%%_album%%_kNoteBracketRight%,
            %_album%
            )
            %_kFolderSep%
         )
   $noop(End album.)

   $noop(Media type.)
      $set(_media,$if2(%_media%,%_kDefaultMedia%)%_kSpace%)
   $noop(End media type.)

   $noop(Disc number, if necessary.)
      $set(_discNum,
         $if($gt(%_totaldiscs%,1),
            $num(%_discNum%,2)%_kPeriod%,
            %_kNull%
            )
         )
   $noop(End end disc number. )

   $noop(Track number.)
   $set(_trackNum,
      $if($and(
            %_trackNum%,
            $or($not(%_isSingle%),$ne(%_album%,%_kNonAlbumTracks%))
            ),
         $num(%_trackNum%,2)%_kTrackSep2%
         )
      )
   $noop(End track number.)
   
   $noop(Title.)
      $set(_title,$rreplace($rreplace($rreplace($rreplace(%_title%,
         %_kReFeat%,%_kNull%),
         %_kMultiSpace%,%_kSpace%),
         %_kRe3Dots%,%_kEllipsis%),
         %_kReAnd%,%_kAmpersand%)
         )
      $set(_title,%_title%%_trackNotes%)
      $set(title,%_title%)
      $set(_title,$rreplace($rreplace($rreplace(%_title%,
         %_kReQuestionMarks%,%_kNull%),
         %_kReQuoteMarks%,%_kSingleQuote%),
         %_kReIllegalFileChars%,%_kTrackSep3%)
         )
$noop(???)
      $set(_trackFile,
         %_artistTrack%%_albumArtistTrack%%_albumTrack%%_discNum%%_trackNum%
         %_title%
         )
   $noop(End title.)
$noop(End set up file/folder names.)

$noop(
   Finally, apply it all to the actual folders and file.
   )
%_albumArtistFolder%%_albumFolder%%_trackFile%

$noop(EDIT HISTORY
   2016-11-01 0.0.4α
      1. Revamped naming convention. Now "Various Artists" is an artist and 
         the album artist goes in the track filename."[Various Artists]" will 
         be a folder at the same level as other artists. Same for "[unknown 
         artist]". "[unknown album]" will get its own folder under each 
         artist, if necessary. "[unknown artist]", "[unknown album]", and 
         "[unknown title]" will be included in track filenames, if necessary.
      2. Updated comments to reflect all that.
      3. Removed a bunch of unnecessary "_kNull"s.
      4. Bug fixes.
   2016-10-28 0.0.3α
      1. Added replacing all occurrances of " and " with " & ".
      2. Added moving articles to the end of title and album.
      3. Tweaked handling for primary/secondary release types.
      4. Bug fixes.
   2016-10-27 0.0.2α
      1. Added handling for all primary/secondary release types.
      2. Tweaked regex for "feat." handling.
      3. Bug fixes.
   2016-10-26 0.0.1α
      1. Initial version.
   )

#8

We call it “tagger script” informally, and that’s about as close to a real name there is. It’s documented at https://picard.musicbrainz.org/docs/scripting/


#9

Did you guys create it? Because I’ve seen at least parts of it, or of something identical, in various tagging apps going back a decade or more. It’s always been only in the file naming options of those apps, never as full scripting.


#10

If you go to https://picard.musicbrainz.org/docs/scripting/ and read it, the very first sentence under the “Syntax” heading (so the 2nd full sentence on the page) says:

The syntax is derived from Foobar2000’s titleformat.


#11

Yaeh, I missed that the first time - went straight to the functions.


#12

A post was split to a new topic: Picard Tagger Script Language Definition for Notepad++


#13

Hello,

I also wrote a renaming script, that I want to share with you. It moves Feat. artists from the artist tag to the title tag, but unlike the ‘Feat. Artists in Titles’ plugin it also detects featured artists without the dots and with ‘ft.’ instead of ‘feat.’.

Some examples:

John Doe ft. Jane Doe - Sample track.ext or John Doe Ft. Jane Doe - Sample track.ext
would be moved to
John Doe/John Doe - Sample track feat. Jane Doe.ext

Jane Doe Feat. John Doe - Lorem ipsum.ext or Jane Doe feat John Doe - Lorem ipsum.ext
would be moved to
Jane Doe/Jane Doe - Lorem Ipsum feat. John Doe.ext

This is the script:

$set(_feat,$rsearch(%artist%,\(?<=\\sfeat\\.\).*|\(?<=\\sft\\.\).*|\(?<=\\sFt\\.\).*|\(?<=\\sFeat\\.\).*))
$set(_feat,$if(%_feat%,%_feat%,$rsearch(%artist%,\(?<=\\sfeat\\s\).*|\(?<=\\sft\\s\).*|\(?<=\\sFt\\s\).*|\(?<=\\sFeat\\s\).*)))
$set(artist,$if(%_feat%,$rreplace(%artist%, feat\\.?.*| Feat\\.?.*| Ft\\.?.*| ft\\.?.*,),%artist%))
%artist%/%artist% - %title%$if(%_feat%,$if($rsearch(%title%,\\sfeat\\.?|\\sFeat\\.?|\\sft\\.?|\\sFt\\.?),, feat.%_feat%),)

Greetings
Phil


#14

I am testing your script and so far, so good. I cannot find a downside with one exception. It appears that I will need to put a bracket around my current A, B, C, etc… album order in my music library. Don’t know if I will have to run everything back through MBP or if just adding brackets will work. This is not a problem. I wish I had had this script 10,000 songs ago when I first started using MBP.

For my needs, this appears to be the perfect script. Very nicely done and really well documented

Thanks to “YIA”!!
Llama lover


#15

Hey,
just quickly driving by to let you know that the link in the first post is expired since the forum is shut down now (atleast I am getting a 503 server error)

Anyway, here is a link that works as long as the wayback machine by archive.org is working:

https://web.archive.org/web/20150801233129/http://forums.musicbrainz.org/viewtopic.php?id=514

A Snapshot of the 5 pages of that old forum post.
My personal favorite is still this one:

$if($eq($left($if2(%albumartist%,%artist%),4),The ),$left($right($if2(%albumartist%,%artist%),$sub($len($if2(%albumartist%,%artist%)),4)),1),$left($if2(%albumartist%,%artist%),1))/$if2(%albumartist%,%artist%)/$if(%date%,$left(%date%,4) -- )%album%/$num(%tracknumber%,2). %artist% - %title%

To get:

root/B/The Beatles/1965 -- Help!/07. The Beatles - Ticket to Ride.mp3
root/V/Various Artists/2005 -- Coup d'État ...

It’s pretty simple and does the job for me.


#17

I am horrible with scripts can someone tell me a simple script to make it Artists First Name Letter/Artists/Album Name/

Then the file nameing convention to be Artist - Title

So for example it would save it to (music folder of my choosing) M/Michael Jackson/Dangerous/ Michael Jackson - Dangerous.mp3

?


#18

Try

$firstalphachar($delprefix(%artist%,prefixes=A,An,The),#)/%artist%/%album%/%artist% - %title%

and see if that does what you want. Note that this files by the track artist and not the album artist because that’s the way you specified it. Personally, I would suggest

$firstalphachar($delprefix(%albumartist%,prefixes=A,An,The),#)/%albumartist%/%album%/%artist% - %title%

instead because this will sort the albums by album artist and then sort the tracks by track artist.


#19

TheBradleys - your script is almost exactly what i am looking for, except that i would lose the A,B,C… level and have Album artist as the listing in the root folder.
Now sorry to wimp out but my head hurts looking at how to do that from yours. Could you post your script with that change?


#20

I had thought I already posted my script, but I guess it slipped my mind.
This script gives a layer of folders with the initial letter of the album artist sort name, then the sort name itself, next the album name, with release comment, and single or EP if appropriate. The songs are in the form: Track number - artist - title. Multiple disc releases are all in the same folder with the disc number tacked on to the front of the track number.
Back at the root level, there are separate folders for soundtracks and various artist compilations. Under those, there’s another layer of initial letters, this time of the swapprefix’ed album names, then those names, with the file names under those in the same format as before.

Examples:
Tagged Music\~D~\Dylan, Bob\Blood on the Tracks\01 - Bob Dylan - Tangled Up in Blue.mp3
Tagged Music\~C~\Crosby, Bing\Bing Sings 96 of His Greatest Hits\711 - Bing Crosby with The Andrews Sisters - Vict’ry Polka.mp3
Tagged Music\Soundtrack\~W~\Wizard of Oz, The\02 - Harold Arlen - Over the Rainbow.mp3
Tagged Music\Various Artists\~1~\1959- Jazz’s Greatest Year\02 - Miles Davis & Gil Evans - The Pan Piper.mp3
Tagged Music\~M~\Mann, Manfred, Earth Band\Blinded by the Light _ Spirit in the Night (Single)\01 - Manfred Mann’s Earth Band - Blinded By The Light.mp3
Tagged Music\~D~\Dire Straits\ExtendedancEPlay (EP)\01 - Dire Straits - Twisting by the Pool.mp3
Tagged Music\~R~\Rush\R40 Live (Only @ Best Buy version with starman flashlight)\210 - Rush - 2112.mp3

    $replace(
    $replace(
    $replace(
    $replace(
    $replace(
    $replace(
    $if($in(%releasetype%,soundtrack),
    	$noop(Soundtracks)
    	Soundtrack/~
    	$left($swapprefix(%album%,A,An,The),1)~/$swapprefix(%album%,A,An,The)
    	$if(%_releasecomment%, \(%_releasecomment%\),$noop())
    	$if($in(%releasetype%,single), \(Single\),$noop())
    	$if($in(%releasetype%,ep), \(EP\),$noop())/
    	$if($gt(%totaldiscs%,1),%discnumber%,$noop())
    	$num(%tracknumber%,2) - %artist% - %title%,
    		$if($eq(%albumartist%,Various Artists),
    		$noop(Various artist albums)
    		Various Artists/~
    		$left($swapprefix(%album%,A,An,The),1)~/$swapprefix(%album%,A,An,The)
    		$if(%_releasecomment%, \(%_releasecomment%\),$noop())
    		$if($in(%releasetype%,single), \(Single\),$noop())
    		$if($in(%releasetype%,ep), \(EP\),$noop())/
    		$if($gt(%totaldiscs%,1),%discnumber%,$noop())
    		$num(%tracknumber%,2) - %artist% - %title%,
    		$noop(Normal albums)
    		~$left($if2(%albumartistsort%,%artistsort%,%albumartist%,%artist%),1)~/
    		$if2(%albumartistsort%,%artistsort%,%albumartist%,%artist%)/%album%
    		$if(%_releasecomment%, \(%_releasecomment%\),$noop())
    		$if($in(%releasetype%,single), \(Single\),$noop())
    		$if($in(%releasetype%,ep), \(EP\),$noop())/
    		$if($gt(%totaldiscs%,1),%discnumber%,$noop())
    		$num(%tracknumber%,2) - %artist% - %title%)
    )
    ,*,[x])
    ,?,)
    ,:,-)
    ,",')
    ,<,{)
    ,>,})

#21

This is mine so far: You can customize it to your liking, which is located at the very bottom.
The default output looks like this:

-=A =-/Amy Winehouse/Back to Black [2007]/Disc 1/Amy Winehouse - Back to Black - 01 - Rehab.mp3

Disc folders are only created if it has more than 2 discs. If you still do not want to display the disc folders, then I recommend changing %Track1% to %Track2%. This will add the disc number 1- to the track number. Just like how it is displayed by default in MusicBee.

$noop( *** DO NOT EDIT THE AREA BELOW | EDITABLE AREA WILL BE AT THE VERY BOTTOM *** )
			$set(MainFolder1,-= $upper($left(%albumartist%,1)) =-/)
			$set(MainFolder2,-= $upper($left(%albumartistsort%,1)) =-/)
			$set(MainFolder3,)
			$set(Artist1,$replace($rreplace(%albumartist%,[_:], -),?,)/)
			$set(Artist2,$replace($rreplace(%albumartistsort%,[_:],-),?,)/)
			$set(Album1,$replace($rreplace(%album%,[_:], -),?,)$if(%date%,$if(%album%, )[$left(%date%,4)])/)
			$set(Album2,$replace($rreplace(%album%,[_:], -),?,)/)
			$set(MultiDisc1,$if($gt(%totaldiscs%,1),Disc $num(%discnumber%,1)/)
			$set(MultiDisc2,)
			$set(PreTitle1,%albumartist% - %album% -)
			$set(PreTitle2,)
			$set(Track1, $num(%tracknumber%,2) - )
			$set(Track2, $num(%discnumber%,1)-$num(%tracknumber%,2) - ))
			$set(Title,%title%)
$noop( *** DO NOT EDIT THE AREA ABOVE| EDITABLE AREA IS JUST BELOW *** )




$noop( *** The Following will use the example of artist: Amy Winehouse and album: Back to Black *** )
$noop( *** Default output: -=A =-/Amy Winehouse/Back to Black [2007]/Disc 1/Amy Winehouse - Back to Black - 01 - Rehab *** )
$noop( *** Change the NUMERICAL value ONLY! Example: %MainFolder1% would be changed to %MainFolder2% *** )
$noop( *** Only change the numerical value to either 1 or 2, anything else will mess things up. *** )
%MainFolder1%	$noop( OPTION 1 -= A=- | OPTION 2 -= W =- | OPTION 3 = No single character folder will be created. )
%Artist1%			$noop( OPTION 1 = Amy WineHouse| OPTION 2 = Winehouse, Amy )
%Album1%			$noop( OPTION 1 = Back to Black [2007] | OPTION 2 = Back to Black )
%MultiDisc1%		$noop( OPTION 1 = If album has more than 1 Disc, then add Disc folders | OPTION 2 = Do not sort by Disc, put all files into a single folder. )
%PreTitle1%		$noop( OPTION 1 = Show Artist and Album in the track title | OPTION 2 = Do not display Artist or Album)
%Track1%			$noop( OPTION 1 = Track Number: 01 | OPTION 2: Track Number: 1-01-> This is best if MultiDisc is set to 2, because you will have 2 track numbers as 01 - *track names*, etc. )
%Title%				$noop( NO OPTION - Just display the name of the track. )

#22

Looks good.
What bugs do you still have? Any idea when you will fix them?


#23

If you are talking about my script, I haven’t noticed any bugs.
But please report any and I will attempt to fix it.
I just wanted to create a script that people can customize to their liking at the very bottom.
Please note that all options should be set to 1 or 2, anything else will mess things up.

Edit: I added that into the script noop.

2nd Edit: I noticed a very minor error and I will fix it tomorrow.


#24

You mean something like this:

$replace($rreplace(
   $if($eq(%albumartist%,Various Artists), [Various Artists],
	    $if($eq(%albumartist%,[unknown]), [Unknown],
          $left($rreplace($if2(%albumartistsort%,%artistsort%),; [^\)]+,), 60))
)
/
$if(%date%,[$left(%date%,4)] )$left($replace(%album%,/,), 70)
/
$if($gt(%totaldiscs%,1),$if(%discnumber%, $num(%discnumber%,2)-),)
$num(%tracknumber%,2). $left(%title%,120),[:?"_]+,),  , )

#25

Here’s the updated version. Fixed a very minor error.

$noop( *** DO NOT EDIT THE AREA BELOW | EDITABLE AREA WILL BE AT THE VERY BOTTOM *** )
			$set(MainFolder1,-= $upper($left(%albumartist%,1)) =-/)
			$set(MainFolder2,-= $upper($left(%albumartistsort%,1)) =-/)
			$set(MainFolder3,)
			$set(Artist1,$replace($rreplace(%albumartist%,[_:*?"<>|],-),?,)/)
			$set(Artist2,$replace($rreplace(%albumartistsort%,[_:*?"<>|],-),?,)/)
			$set(Album1,$replace($rreplace(%album%,[_:*?"<>|], -),?,)$if(%date%,$if(%album%, )[$left(%date%,4)])/)
			$set(Album2,$replace($rreplace(%album%,[_:*?"<>|], -),?,)/)
			$set(MultiDisc1,$if($gt(%totaldiscs%,1),Disc $num(%discnumber%,1)/)
			$set(MultiDisc2,)
			$set(PreTitle1,$replace($rreplace(%albumartist% - %album% -,[_:*?"<>|], -),?,))
			$set(PreTitle2,)
			$set(Track1, $num(%tracknumber%,2) - )
			$set(Track2, $num(%discnumber%,1)-$num(%tracknumber%,2) - ))
			$set(Title,$replace($rreplace(%title%,[_:*?"<>|],),?,))
$noop( *** DO NOT EDIT THE AREA ABOVE| EDITABLE AREA IS JUST BELOW *** )




$noop( *** The Following will use the example of artist: Amy Winehouse and album: Back to Black *** )
$noop( *** Default output: -=A =-/Amy Winehouse/Back to Black [2007]/Disc 1/Amy Winehouse - Back to Black - 01 - Rehab *** )
$noop( *** Change the NUMERICAL value ONLY! Example: %MainFolder1% would be changed to %MainFolder2% *** )
$noop( *** Only change the numerical value to either 1 or 2, anything else will mess things up. *** )
%MainFolder1%	$noop( OPTION 1 -= A=- | OPTION 2 -= W =- | OPTION 3 = No single character folder will be created. )
%Artist1%			$noop( OPTION 1 = Amy WineHouse| OPTION 2 = Winehouse, Amy )
%Album1%			$noop( OPTION 1 = Back to Black [2007] | OPTION 2 = Back to Black )
%MultiDisc1%		$noop( OPTION 1 = If album has more than 1 Disc, then add Disc folders | OPTION 2 = Do not sort by Disc, put all files into a single folder. )
%PreTitle1%		$noop( OPTION 1 = Show Artist and Album in the track title | OPTION 2 = Do not display Artist or Album)
%Track1%			$noop( OPTION 1 = Track Number: 01 | OPTION 2: Track Number: 1-01-> This is best if MultiDisc is set to 2, because you will have 2 track numbers as 01 - *track names*, etc. )
%Title%				$noop( NO OPTION - Just display the name of the track. )

Looking for the ultimate renaming script!
#26

How do you deal with naming when you have albums which are different editions/versions? For me the album names are the same, so it tried to put all the files into the same folder.


#27

The way I do it here is to include the release date in the directory naming scheme.