MP3-Find

 view release on metacpan or  search on metacpan

Changes  view on Meta::CPAN

Revision history for Perl extension MP3::Find.

0.07  7 Jun 2011
    - fixed tests that were failing due to a bad test plan

0.06  11 Jul 2006
    - deprecated the create_db, update_db, and sync_db methods
    - databases can be selected by a custom DSN or an already open database handle

0.05  28 Apr 2006
    - mp3find searches in ID3v2 tags if MP3::Tag is available
    - using Sort::Key for sorting of results (if available)

0.04  2 Apr 2006
    - BUGFIX: fixed tests that were failing because the test mp3 was not included
    - added "status_callback" option to DB backend constructor

0.03  27 Mar 2006
    - added "exclude_path" option to filesystem backend
    - added "sync_db" method to the DB backend
    - added support for searching by ID3v2 tag (using MP3::Tag)

0.02  1 Feb 2006
    - doc updates to MP3::Find (thanks to Mike Slass for the suggestion)
    - added a test suite for the DB backend
    - DB management functions are now in the DB backend
    - rewrote (and documented) mp3db to use the new DB backend functions

0.01  29 Jan 2006
    - first CPAN release

README  view on Meta::CPAN

                title => 'deep in the am',
            },
            ignore_case => 1,
            exact_match => 1,
            sort => [qw(year album tracknum)],
            printf => '%2n. %a - %t (%b: %y)',
        );

REQUIRES
    File::Find, MP3::Info, and Scalar::Util are needed for the filesystem
    backend (MP3::Find::Filesystem). In addition, if MP3::Tag is available,
    you can search by explicit ID3v2 tag frames.

    DBI, DBD::SQLite, and SQL::Abstract are needed for the database backend
    (MP3::Find::DB).

COPYRIGHT AND LICENSE
    Copyright (c) 2006 by Peter Eichman. All rights reserved.

    This program is free software; you can redistribute it and/or modify it
    under the same terms as Perl itself.

lib/MP3/Find.pm  view on Meta::CPAN


B<Note the second>: This whole project is still in the alpha stage, so
I can make no guarentees that there won't be significant interface changes
in the next few versions or so. Also, comments about what about the API
rocks (or sucks!) are appreciated.

=head1 REQUIRES

L<File::Find>, L<MP3::Info>, and L<Scalar::Util> are needed for
the filesystem backend (L<MP3::Find::Filesystem>). In addition,
if L<MP3::Tag> is available, you can search by explicit ID3v2
tag frames.

L<DBI>, L<DBD::SQLite>, and L<SQL::Abstract> are needed for the
database backend (L<MP3::Find::DB>).

=head1 EXPORTS

=head2 find_mp3s

    my @results = find_mp3s(%options);

lib/MP3/Find/Filesystem.pm  view on Meta::CPAN

use MP3::Find::Util qw(get_mp3_metadata);

eval {
    require Sort::Key;
    Sort::Key->import(qw(multikeysorter));
    require Sort::Key::Natural;
};
my $USE_SORT_KEY = $@ ? 0 : 1;


eval { require MP3::Tag };
my $CAN_USE_ID3V2 = $@ ? 0 : 1;

use_winamp_genres();

sub search {
    my $self = shift;
    my ($query, $dirs, $sort, $options) = @_;
    
    # prep the search patterns as regexes
    foreach (keys(%$query)) {

lib/MP3/Find/Filesystem.pm  view on Meta::CPAN

        my $ref = ref $$options{exclude_path};
        if ($ref eq 'ARRAY') {
            $$options{exclude_path} = '(' . join('|', @{ $$options{exclude_path} }) . ')';
        }
        unless ($ref eq 'Regexp') {
            $$options{exclude_path} = qr[$$options{exclude_path}];
        }
    }
    
    if ($$options{use_id3v2} and not $CAN_USE_ID3V2) {
	# they want to use ID3v2, but don't have MP3::Tag
	warn "MP3::Tag is required to search ID3v2 tags\n";
    }
	
    # run the actual find
    my @results;
    find(sub { match_mp3($File::Find::name, $query, \@results, $options) }, $_) foreach @$dirs;
    
    # sort the results
    if (@$sort) {
	if ($USE_SORT_KEY) {
	    # use Sort::Key to do a (hopefully!) faster sort

lib/MP3/Find/Filesystem.pm  view on Meta::CPAN

            artist => 'ilyaimy',
            album  => 'myxomatosis',
        },
        ignore_case => 1,
    );

=head1 REQUIRES

L<File::Find>, L<MP3::Info>, L<Scalar::Util>

L<MP3::Tag> is also needed if you want to search using ID3v2 tags.

=head1 DESCRIPTION

This module implements the C<search> method from L<MP3::Find::Base>
using a L<File::Find> based search of the local filesystem.

=head2 Special Options

=over

=item C<exclude_path>

Scalar or arrayref; any file whose name matches any of these paths
will be skipped.

=item C<use_id3v2>

Boolean, defaults to false. If set to true, MP3::Find::Filesystem will
use L<MP3::Tag> to get the ID3v2 tag for each file. You can then search
for files by their ID3v2 data, using the four-character frame names. 
This isn't very useful if you are just search by artist or title, but if,
for example, you have made use of the C<TOPE> ("Orignal Performer") frame,
you could search for all the cover songs in your collection:

    $finder->find_mp3s(query => { tope => '.' });

As with the basic query keys, ID3v2 query keys are converted to uppercase
internally.

lib/MP3/Find/Util.pm  view on Meta::CPAN

use warnings;

use base qw(Exporter);
use vars qw(@EXPORT_OK);

@EXPORT_OK = qw(build_query get_mp3_metadata);

use Carp;
use MP3::Info;

eval { require MP3::Tag };
my $CAN_USE_ID3V2 = $@ ? 0 : 1;

sub build_query {
    my @args = @_;
    
    # first find all the directories
    my @dirs;
    while (local $_ = shift @args) {
        if (/^-/) {
            # whoops, there's the beginning of the query

lib/MP3/Find/Util.pm  view on Meta::CPAN

    my $filename = $args->{filename} or croak "get_mp3_metadata needs a 'filename' argument";
    
    my $mp3 = {
        FILENAME => $filename,
        %{ get_mp3tag($filename)  || {} },
        %{ get_mp3info($filename) || {} },
    };
    
    if ($CAN_USE_ID3V2 and $args->{use_id3v2}) {
	# add ID3v2 tag info, if present
	my $mp3_tags = MP3::Tag->new($filename);
	unless (defined $mp3_tags) {
	    warn "Can't get MP3::Tag object for $filename\n";
	} else {
	    $mp3_tags->get_tags;
	    if (my $id3v2 = $mp3_tags->{ID3v2}) {
		for my $frame_id (keys %{ $id3v2->get_frame_ids }) {
		    my ($info) = $id3v2->get_frame($frame_id);
		    if (ref $info eq 'HASH') {
			# use the "Text" value as the value for this frame, if present
			$mp3->{$frame_id} = $info->{Text} if exists $info->{Text};
		    } else {
			$mp3->{$frame_id} = $info;



( run in 0.848 second using v1.01-cache-2.11-cpan-d7a12ab2c7f )