For Classical Music there are two parallel hierachies, the standard Artist/Track/Album, but also the Composer/Movement/Work hierachy. This Composer, Movement and Work hierachy is critical for Classical Music listening and allows us to view our music collection categorized by Composer and Works instead of just byAlbum Artist and Album.
SongKong add both hierachies to our songs, but the calculation of Work and Movement is surpisingly complicated so I have summarized the algorithm below.
1. If Album Is Classical
Although popular music also has works this is usually at just a single level, song is a recording of work, and both the performer and composer are usually the same. Popular music does not usually have a Work AND Movement so we do not set these fields for albums that are not Classical, although we still set the MB Recording Work field so the information is available.
Since MusicBrainz does not store an Is classical flag the algorithm uses various heuristics to decide if a release is classical or not, this is not currently documented.
2. Group Tracks By Work
This group tracks by MusicBrainz Work if the track has at least two levels of work so represents movement and work, if the track does not have any MusicBrainz Work we look at the title instead and if this seems to represent Work : Title we group by that work instead. We don’t group tracks that have none or only one level of work. We prefer to prefer to group by MusicBraiz Works because this is the most reliable method.
For each Track
If Track is recording of Work (Work1) and that Work is part of a larger Work (Work2)
Group Track By Work2
Else if only have Work1 dont group
Else If don't have MusicBrainz Works
If Title contains :
Split at :
Check left handside is not composer name
If not Composer then Work name is to left of colon and group by this
Else
Dont Group this Track
3. Set Best Work Name for each Work
We now set the best work name for each Work, although we prefer to use MusicBrainz for grouping tracks by work, we prefer to use the song title to set the final work name. This is because this will better reflect how the customer knows the work, most notably it means likely that the Work name will be in the language/script that the customer is familar with.
For Each Work
Get the Tracks for Work
Get the Composers for Work
For each Track
if(only have one Composer)
If Title contains :
Set Work from Title
For each Track
Create set of Work Titles Created
If Only one Work Title Created
If not all tracks have set a Work
Set missing ones to the Work Title if can find Work Title in the Title
If Unable to get Work Name
Use the Work Name created in Stage 2 (usually from MusicBrainz)
4. Check Work Name Consistency
As explained in Stage 3 we prefer to use Work derived from title, however if this is not possible for all works on the release then we set the work title from stage 2 (usually from MusicBrainz). We do this in order to get more consistency over work names then we are likley to get if some names are derived from titles and some from MusicBrainz works.
for each Track
Is Work Name derived from Title
if(not all work names derived from Title)
Set Work name from name in created in Stage 2 (usually MusicBrainz)
5. Set Movement and Part for Each Track
We now create a MovementAndWork objects for each Track that gathers all the work related information
for each Work
Get Composers for Tracks in Work
Set ComposerName = if Composers = 1
Set IsContiguous = Are all Tracks Contigously listed in release
for each Track
Create MovementAndWork object
Set Work Name from previous calculation
Set How many Movements in Work found on this release
Set Is MultiLevel
Set Overall Work
If have MusicBrainz Works highest level Work in MusicBrainz Work Hierachy
Else set to Work
Calculate Movement and Part Fields
If(title contains :)
Part = Part after the Colon
Part No= Part number part
Movement = Part after stripping any numbers
Else if Only have one track from Work on Release
Part = Title
Part No= Part number part
Movement = Part after stripping any numerals
Else if Have MusicBrainz Works
Part= MusicBrainz Work 1
Part No=Part number part
Movement = Part after stripping any numerals
Else
Part = Title
Movement = Title after stripping any numerals
6. Apply to Fields
We should now have preferred values for the following fields:
- Work
- Overall Work
- Movement
- Part
- Part No
There are also some additional details for MinimServer and Opera Work format
MinimServer Group field
When you play a Classical work with MinimServer enabling this option will show the composer when you play the work, includes adding composer to title if the work has no movements
If IsContiguous=true and more than one track from Work in release
If Single ComposerName for Work and If Add Composer to MinimServer Group option enabled
Set MinimServer Group to Composer Last Name:Work
Else we set MinimServer Group to Work
Overall Work field
When using MinimServer enabling this option will show the composer as part of the work name in the Work index
If Single ComposerName for Work and and have Composer to Overall Work option enabled
Set OverallWork= Composer Last name:Overall Work
Opera Works
Opera Works simply means tracks that have a Movement Work, parent Work and at least one additional Work that is parent of the Work. This is typical in Opera where we often have a hierachy of Scene, Act and Opera. When we have this number of levels Overall Work in the MovementAndWork object is the top level Work
If we detect that Overall Work is different to Work then we set multi level fields as follows
if(Opera Work Format==MinimServer)
Work field=MovementAndWork.Work
Overall Work field=MovementAndWork.OverallWork
Else if(Opera Work Format==Roon)
Section field=MovementAndWork.Work
Work field=MovementAndWork.OverallWork
Else if(Opera Work Format==Lyrion)
Grouping field=MovementAndWork.Work
Work field=MovementAndWork.OverallWork