#! /usr/bin/perl # A simple program to copy podcasts from source directories # under $SOURCE of the form yyyymmdd to directories # arranged in the same way under $TARGET on a music player. # I use perlpodder which by default, creates directories with such names. # If you don't have File::Remove or File::Copy::Recursive # and you have rm and cp, then you could uncomment the calls to system # and comment out the calls to remove and dircopy. # Copyright (C) 2008 Nick Urbanik # This program is free software; you can redistribute it and/or # modify it under the terms of the GNU General Public License # as published by the Free Software Foundation; either version 2 # of the License, or (at your option) any later version. # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # You should have received a copy of the GNU General Public License # along with this program; if not, write to the Free Software # Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. use strict; use warnings; use File::Copy; use Getopt::Long; use File::Remove 'remove'; use File::Copy::Recursive 'dircopy'; use Readonly; # These first four are what you would want to customise: Readonly my $TARGET => '/media/E100/Music'; Readonly my $SOURCE => "$ENV{HOME}/podcasts"; Readonly my $GLOBPAT => '20[0-9][0-9][0-9][0-9][0-9][0-9]'; # Delete all but the last 7 podcast directories by default: my $deldays = 7; my $target = $TARGET; my $source = $SOURCE; my $globpat = $GLOBPAT; sub usage { ( my $prog = $0 ) =~ s{.*/}{}; print < \$deldays, 'target=s' => \$target, 'source=s' => \$source, 'globpat' => \$globpat, 'dry-run' => \$dry_run, debug => \$debug, help => sub { usage }, ) or usage; warn "positive del-days needed\n" and usage if defined $deldays and $deldays <= 0; print "Will delete *all* but the last $deldays podcast directories ", "on the music player.\n\n" if $deldays; die "Music player not mounted\n" unless -d $target; die "Cannot find source directory $source\n" unless -d $source; my @source_dirs = map { ( my $sdir = $_ ) =~ s(.*/)(); $sdir } glob( "$source/$globpat" ); my $latest_t_dir = ( glob( "$target/$globpat" ) )[ -1 ]; my $latest_s_dir = $source_dirs[ -1 ]; $latest_t_dir =~ s{.*/}{}; # Find what's missing in $latest_t_dir: my %have_file = map { ( my $tfile = $_ ) =~ s{.*/}{}; $tfile => 1 } glob( "$target/$latest_t_dir/*" ); my @src_files = map { ( my $sfile = $_ ) =~ s{.*/}{}; $sfile } glob( "$source/$latest_t_dir/*" ); # Then copy files that are missing # from $source/$latest_t_dir to $target/$latest_t_dir FILE: foreach my $sf ( @src_files ) { if ( not exists $have_file{$sf} ) { print qq{copy "$source/$latest_t_dir/$sf", "$target/$latest_t_dir"\n}; next FILE if $dry_run; copy "$source/$latest_t_dir/$sf", "$target/$latest_t_dir" or die qq{Cannot copy "$source/$latest_t_dir/$sf", }, qq{"$target/$latest_t_dir"}; } } # Now copy the remaining directories: SOURCE_DIR: foreach my $sd ( @source_dirs ) { next SOURCE_DIR unless $sd gt $latest_t_dir; my @files = map { ( my $sfile = $_ ) =~ s{.*/}{}; $sfile } glob( "$source/$sd/*" ); print "Copying @files from $source/$sd to '$target'\n"; next SOURCE_DIR if $dry_run; #system( "cp -av $source/$sd $target" ) == 0 or die "failed to copy $sd: $?"; dircopy( "$source/$sd", "$target/$sd" ) or die "Failed to copy $sd: $!"; } exit 0 unless $deldays; my @music_dirs = map { ( my $sdir = $_ ) =~ s(.*/)(); $sdir } glob( "$target/$globpat" ); my @del_dirs = @music_dirs[ 0 .. $#music_dirs - $deldays ] or exit 0; print "About to delete these directories from music player: @del_dirs\n"; DEL_DIR: foreach my $sd ( @del_dirs ) { print "Recursively deleting '$target/$sd'...\n" if $debug; next DEL_DIR if $dry_run; remove \1, "$target/$sd" or die "Unable to recursively delete '$target/$sd'\n"; # system( "rm -rf $target/$sd" ) == 0 or die "failed to delete $sd: $?"; }