| Net-iTMS documentation | Contained in the Net-iTMS distribution. |
Net::iTMS::Album - Represents an album in the iTunes Music Store
use Net::iTMS::Album;
my $album = Net::iTMS::Album->new($iTMS, $id);
print "Album: ", $album->title, "\n";
# $track will be a Net::iTMS::Song object
for my $track ($album->tracks) { # also $album->songs
print "\t ", $track->number, ": ", $track->title, "\n";
}
Net::iTMS::Album represents an album in the iTMS and encapsulates the associated data. If a piece of information hasn't been fetched from the iTMS, it will transparently fetch and store it for later use before returning.
If any method, excepting id, record_label, and thumb, is called,
the information for the others will be fetched in the same request. This
means, for these methods, the first call to one will have a time hit for the
HTTP request, but subsequent calls won't.
The first argument must be an instance of Net::iTMS, the second an iTMS album ID.
Returns a blessed hashref (object) for Net::iTMS::Album.
Returns the ID of the album (albumId).
Returns the title of the album.
Returns a Net::iTMS::Artist object for the album's artist.
Returns a Net::iTMS::Genre object for the album's genre.
Returns a hashref with the keys url, width, and height which
are for the album's cover.
Returns a hashref with the keys url, width, and height which
are for the thumbnail of the album's cover (if available).
Returns an array or arrayref (depending on context) of Net::iTMS::Song objects representing the tracklist of the album (in order of track number).
Returns the total number of songs on the album available from the iTMS.
Returns the release date of the album (if available).
Returns the copyright information for the album (if available).
Returns an arrayref of hashrefs representing the album's "path" in the iTMS. The hashrefs contain the name of the node in the path and the iTMS URL of that node.
Copyright 2004, Thomas R. Sibley.
You may use, modify, and distribute this package under the same terms as Perl itself.
Thomas R. Sibley, http://zulutango.org:82/
| Net-iTMS documentation | Contained in the Net-iTMS distribution. |
package Net::iTMS::Album; # # Written by Thomas R. Sibley, <http://zulutango.org:82/> # use warnings; use strict; use vars '$VERSION'; $VERSION = '0.15'; use Net::iTMS::Error; use overload '""' => sub { shift->as_string }, fallback => 1; sub as_string { my $self = shift; return defined $self ? $self->name : undef; }
sub new { my ($class, $itms, $id, %prefill) = @_; my $self = bless { id => $id, error => '', debug => defined $itms->{debug} ? $itms->{debug} : 0, _itms => $itms, }, $class; if (%prefill) { $self->{$_} = $prefill{$_} for keys %prefill; } return $self; }
sub id { return $_[0]->{id} } sub title { my $self = shift; $self->_get_basic_info if not exists $self->{title}; return $self->{title}; } sub name { return $_[0]->title } sub artist { my $self = shift; $self->_get_basic_info if not exists $self->{artist}; return $self->{artist}; } sub genre { my $self = shift; $self->_get_basic_info if not exists $self->{genre}; return $self->{genre}; } sub cover { my $self = shift; $self->_get_basic_info if not exists $self->{cover}; return $self->{cover}; } sub thumb { my $self = shift; return $self->{thumb}; } sub record_label { my $self = shift; return $self->{record_label}; } sub copyright { my $self = shift; $self->_get_basic_info if not exists $self->{copyright}; return $self->{copyright}; } sub released { my $self = shift; $self->_get_basic_info if not exists $self->{released}; return $self->{released}; } sub tracks { my $self = shift; $self->_get_basic_info if not exists $self->{tracks}; return wantarray ? @{$self->{tracks}} : $self->{tracks}; } sub songs { return $_[0]->tracks } sub total_songs { my $self = shift; $self->_get_basic_info if not exists $self->{total_songs}; return $self->{total_songs}; } sub info { my $self = shift; $self->_get_basic_info if not exists $self->{info}; return wantarray ? @{$self->{info}} : $self->{info}; } sub notes { my $self = shift; $self->_get_basic_info if not exists $self->{notes}; return wantarray ? @{$self->{notes}} : $self->{notes}; } sub path { my $self = shift; $self->_get_basic_info if not exists $self->{path}; return wantarray ? @{$self->{path}} : $self->{path}; } # # This populates the basic data from a viewAlbum request # sub _get_basic_info { my $self = shift; my $twig = $self->{_itms}->{_request}->url('viewAlbum', $self->id); my $root = $twig->root; my $path = $root->first_child('Path'); my $sv = $root->first_child('ScrollView'); $self->{genre} = $self->{_itms}->get_genre($root->att('genreId')); # # Path # for my $child ($path->children('PathElement')) { push @{$self->{path}}, { name => $child->att('displayName'), url => $child->trimmed_text, }; } $path->delete; # # Name and cover # # We could just depend on the right twig being the first # in the document everytime, but let's not # my $album; for my $child ($sv->descendants('ViewAlbum')) { if (defined $child->{att}{draggingName} and $child->first_child_matches('PictureView')) { # This is the one we want, so break out $album = $child; last; } } $self->{title} = $album->att('draggingName'); my $pic = $album->first_child('PictureView'); $self->{cover} = { height => $pic->att('height'), width => $pic->att('width'), url => $pic->att('url'), }; $pic->delete; $album->delete; if ($root->att('genreId') == 50000024) { # have to bail for now $sv->delete; $twig->purge; return; } # # Artist # if (not defined $self->{artist}) { my $artist; for my $child ($sv->descendants('ViewArtist')) { if (defined $child->{att}{id} and $child->{att}{id} eq $root->att('artistId')) { # This is the one we want, so break out $artist = $child; last; } } if (defined $artist) { $self->{artist} = $self->{_itms}->get_artist( $root->att('artistId'), name => $artist->trimmed_text, ); $artist->delete; } } # # Info # for my $text ($sv->first_child('MatrixView') ->first_child('VBoxView') ->first_child('MatrixView') ->first_child('VBoxView') ->children('TextView')) { if ($text->contains_only_text and $text->trimmed_text ne '') { my $val = $text->trimmed_text; push @{$self->{info}}, $val; $val =~ s/^\s*//; $val =~ s/\s*$//; if ($val =~ s/^Release Date:\s*//) { $self->{released} = $val; } elsif ($val =~ s/^Total Songs:\s*//) { $self->{total_songs} = $val; } elsif ($val =~ s/^Genre:\s*//) { $self->{genre}{name} = $val; } elsif ($val =~ s/^.+\s*(?>\d{4})//) { $self->{copyright} = $val; } } } # # Notes # my $notes = $sv->first_child('MatrixView') ->first_child('VBoxView') ->last_child('HBoxView'); if (defined $notes) { $notes = $notes->first_child('VBoxView'); if (defined $notes) { for my $text ($notes->first_child('TextView') ->next_siblings('TextView')) { push @{$self->{notes}}, $text->trimmed_text; } } $notes->delete; } $sv->delete; # # Tracks # my $plist = $root->first_child('TrackList') ->first_child('plist') ->first_child('dict') ->first_child('array'); $self->{tracks} = [ ]; for my $dict ($plist->children('dict')) { my %data; for my $key ($dict->children('key')) { $data{$key->trimmed_text} = $key->next_sibling('#ELT')->trimmed_text; } $data{releaseDate} =~ s/A-Za-z//g; $data{copyright} =~ s/^.+\s*(?>\d{4})//; $data{copyright} =~ s/\s*$//; push @{$self->{tracks}}, $self->{_itms}->get_song( $data{songId}, title => $data{songName}, album => $self, artist => $self->{artist}, genre => $self->{_itms}->get_genre( $data{genreId}, name => $data{genre}, ), year => $data{year}, number => $data{trackNumber}, count => $data{trackCount}, disc_number => $data{discNumber}, disc_count => $data{discCount}, explicit => $data{explicit}, comments => $data{comments}, copyright => $data{copyright}, preview_url => $data{previewURL}, released => $data{releaseDate}, price => $data{priceDisplay}, vendor => $data{vendorId}, ); } $plist->delete; $twig->purge; $self->{total_songs} = $self->{tracks}[0]{count} if not $self->{total_songs}; }
42;