With the introduction of iTunes 12.2 a few months back, quite a few things changed for users and software vendors alike. One of the things that didn't come to my attention until recently is an oddity having to do with album ratings. It seems that hardly anyone really uses them, but if you have rated a couple of songs, iTunes displays an average of those ratings as the album rating. To signal that the values are computed rather than entered, they appear as gray stars as opposed to solid black stars. What happened when iTunes 12.2 was introduced is, that apparently some albums got ratings—nobody really knows where from. This resulted in all the unrated songs also showing ratings—gray ones, as they are computed, not entered. Obviously, everybody using smart playlists based on song ratings suffered.

Quite a bit.

A simple solution to the problem is to reset all album ratings to zero manually. Not very fun. When asked how to best solve the issue, I immediately figured that a library batch action can do the job. Library batch actions are little beaTunes plugins (often beaTlets), that do the same thing for all items in your beaTunes/iTunes library and can easily be scripted in Groovy/Jython/JRuby. So a library batch action for this particular problem really only needs to reset the album rating to 0 for all songs with an album rating other than 0 .

Here's the Groovy code (download):

import javax.swing.Action import java.awt.* import org.slf4j.LoggerFactory import com.tagtraum.beatunes.action.standard.LibraryBatchAction import com.tagtraum.beatunes.action.standard.LibraryBatchAction.EachSongProcessor import com.tagtraum.beatunes.MessageDialog import javax.swing.JOptionPane import com.tagtraum.audiokern.AudioSong // An action that allows to reset all album ratings. // The corresponding menu item can be found in the 'Tools' menu. class ResetAlbumRatings extends LibraryBatchAction { // Inner class that implements the // com.tagtraum.beatunes.action.standard.LibraryBatchAction.EachSongProcessor // interface. Its process method is called for each song. class Resetter implements EachSongProcessor { static log = LoggerFactory.getLogger("ResetAlbumRatings.groovy") String file // Called once, before processing starts. def void startProcessing(int count) { log.info "We are expecting to embed ratings for ${count} songs." } // Called for each song. def void process(AudioSong song, int index) { int rating = song.getAlbumRating() boolean computed = song.isAlbumRatingComputed() // added as of 11/5/2015 if (rating > 0 && computed) { // && computed song.setAlbumRating(1) // set to 1 instead of 0 log.info("Reset album rating for " + song) } else { log.info("No rating set in " + song) } } // Called once all songs were processed. def void finishProcessing() { log.info "Done." new MessageDialog(getApplication().getMainWindow(), "Done.", JOptionPane.INFORMATION_MESSAGE, JOptionPane.DEFAULT_OPTION).showDialog() } // Message to be shown in progress dialog. def String getProgressDialogMessage(AudioSong song) { "Resetting album rating of ${song.getName()}" } // Title for progress dialog. def String getProgressDialogTitle() { "Resetting album ratings ..." } } // Unique id def String getId() { "Groovy.ResetAlbumRatings" } // Is called by beaTunes as part of the lifecycle after instantiation. // At this point all other plugins are instantiated and registered. // We use this to set the menu item's (i.e. action's) name. def void init() { putValue(Action.NAME, "Reset Album Ratings") } // We need to ask the user, whether he really wants to do this. // How we ask is defined here. def String getConfirmationMessage() { "Do you really want to the album ratings of all your files?" } // Factory method that creates the processor for each song. def EachSongProcessor createEachSongProcessor() { new Resetter() } }

You can install this like any other plugin—just make sure the code is in a file called ResetAlbumRatings.groovy (the file name must be the same as the main class name). To reset all album ratings in your library, restart beaTunes after the plugin installation, and open the Tools menu. There should now be a new item called Reset Album Ratings (see init() in the code). When running this action, please be careful: You won't get to say "yes" or "no" for each individual album. That's why it's called a batch action. Also, changes cannot be undone.

Library batch actions are a great way to fix something in your entire library. And it's not rocket science. Basic understanding of Groovy (or some other popular scripting language) is typically all you need.

Update 11/5/2015

I have changed the script slightly, as a response to... well... it not working. Please re-install the script and make sure it contains the line boolean computed = song.isAlbumRatingComputed() . Also, the script may still be applying changes in the background, even after it reports that it's done. Give it a couple of minutes (or check the beaTunes logs for activity). Thanks for your feedback!

Labels: beaTlet, iTunes, Plugin