#! /usr/bin/perl # Copyright Eric Koldinger, 2006 # kolding @ koldware.com # No warranty, expressed, or implied, if you use this program. Author is not responsible for any # damage it may do to your files or sanity. use Getopt::Long; use Sys::Hostname; use Sys::Syslog; use Mail::Sendmail; use CDDB::File; use POSIX; # Set up options processing $dir = "/tmp/music"; $mail = $ENV{"USER"} . "@" . hostname(); $help = 0; $sleep = 30; $verbose = 0; $maxLoops = 0; $quietABCDE = 0; $notify = 0; $daemon = 0; $nice = 0; $script = "/usr/local/bin/abcde"; $result = GetOptions( "dir=s" => \$dir, "sleep=i" => \$sleep, "verbose!" => \$verbose, "loops=i" => \$maxLoops, "address=s" => \$mail, "notify!" => \$notify, "nice=i" => \$nice, "quietabcde!" => \$quietABCDE, "daemon!" => \$daemon, "script" => \$script, "help" => \$help ); if (!$result) { print "GetOptions failed: $result\n"; } if ($help || !$result) { usage(); exit; } if ($daemon) { openlog("Autoencode", "", "user"); } $quietABCDE = 1 if ($daemon); $verbose = 0 if ($daemon); POSIX::nice($nice) if ($nice); chdir $dir || die "Could not change to target directory: $dir\n"; $loops = 0; while (1) { ## Keep a count of how many were processed on this iteration. ## If greater than 0, we won't sleep. $processed = 0; opendir(DIRHANDLE, $dir); @entries = readdir(DIRHANDLE); closedir(DIRHANDLE); foreach $entry (@entries) { next if (!($entry =~ /^abcde.[0-9a-fA-F]+$/)); ($abcde, $discid) = split /\./, $entry; if (abcdeReady($entry)) { print "$abcde ($entry) ready\n" if $verbose; $processed++; $command = "$script -C $discid"; $command .= " >& /dev/null" if $quietABCDE; print "Executing: $command\n" if $verbose; $result = system ($command); message("Encoding DISC ID $discid completed. $result"); checkError($entry, $discid); } else { print "$abcde ($entry) not ready\n" if $verbose; } } $loops++; if ($maxLoops != 0 && $loops >= $maxLoops) { message("Maximum iterations ($maxLoops) reached. Exiting."); exit; } if (!$processed) { print "Sleeping for $sleep minutes\n" if $verbose; sleep ($sleep * 60); message("Looking for files to process in $dir"); } } sub abcdeReady { my $abcdeDir = shift; return 0 if (defined $processed{$abcdeDir}); return 0 if (!-d $abcdeDir); return 0 if (!-e "$abcdeDir/status"); return 0 if (!-e "$abcdeDir/cdparanoia-audio-tracks"); return 0 if (-e "$abcdeDir/errors"); open PARANOIA, "$abcdeDir/cdparanoia-audio-tracks" || return 0; while () { chomp; $tracks = $_; } close PARANOIA; print "$abcdeDir: Tracks $tracks\n" if $verbose; my $readsComplete = 0; open STATUS, "$abcdeDir/status" || return 0; while () { chomp; $readsComplete++ if (/readtrack-[0-9]+/); } close STATUS; printf("$abcdeDir: Reads Complete $readsComplete\n") if $verbose; return 0 if ($readsComplete != $tracks); $processed{$abcdeDir} = 1; return 1; } sub checkError { my ($entry, $discid) = @_; if (-e "$dir/$entry/errors") { message( "Encoding run on DISC ID: $discid ($dir/$entry) Failed"); if ($notify) { my $subject = "Autoencode: Encoding run on DISC ID: $discid ($dir/$entry) Failed"; my $mailMessage = "Encoding run on DISC ID: $discid Failed\n"; my $cddb = CDDB::File->new("$dir/$entry/cddbread.1"); $mailMessage .= "Probable Artist: " . $cddb->artist() . "\n"; $mailMessage .= "Probable Title: " . $cddb->title() . "\n"; $mailMessage .= "\n\n"; open ERROR, "< $dir/$entry/errors"; while () { chomp; $mailMessage .= $_ . "\n"; } close ERROR; my %mail = ( To => $mail, From => "root@" . hostname(), Subject => $subject, Message => $mailMessage ); sendmail(%mail) or message("Unable to send mail: " . $Mail::Sendmail::error, "error"); } } } sub usage { print "Usage\n"; print ; } sub message { my $message = shift; my $level = shift; $level = "notice" if (!defined $level); print $message, "\n" if $verbose; syslog("notice", $message) if $daemon; } __DATA__ -d dir --dir=directory Where to look for abcde files. -s n --sleep=n Sleep for N minutes before checking for files again -n --[no]notify Send mail for failing runs. -a addr --address=addr Address to send mail to. -q --quietabcde Tell ABCDE to shut up even more. -d --daemon Run as a daemon. Log to syslog. -l i --loops=i Run for loops. -s path --script=path Path to abcde. -v --verbose Talk more to stdout. -h --help This screen.