#!/usr/bin/perl # 1. the getopts ( -u ) # 2. the update usage() # 3. modify rsync command so we get understand # our needed packages use strict "vars"; use Getopt::Std; # Global Variables my $VERBOSE = 0; my $DEBUG = 0; # commandline options # -D # -l my $opt_string = "vdhD:H:l:su:"; getopts( "$opt_string", \my %opt) or usage() and exit(1); $VERBOSE = 1 if $opt{'v'}; $DEBUG = 1 if $opt{'d'}; if ( $opt{'h'} ){ usage(); exit 0; } my $HOST = $opt{H}; my $DIR = $opt{D}; my $LOCAL = $opt{l}; my $SIMULATE = $opt{s}; my $USER = $opt{u}; my $ITERATIONS = 3; usage() and die("you need to supply a hostname\n") unless $HOST; usage() and die("you need to supply a remote directory\n") unless $DIR; $LOCAL = $HOST unless $LOCAL; debug("Checking if host is up and folder is present\n"); die("The remote host could not verify the directory $DIR or is down. Exiting.\n") unless verify_host($HOST,$DIR,$USER); ########################################################## # main part # remove the oldest if number equals $ITERATIONS my $oldest = $LOCAL . "." . $ITERATIONS; verbose("Removing oldest directory: $oldest\n"); if ( stat($oldest)){ system("rm -rf $oldest") unless $SIMULATE; } else { debug("Directory $oldest missing, skipping delete\n"); } # rotate the folders from 1 until the end, backwards for ( my $i = ( $ITERATIONS -1); $i >= 1; $i--){ my $new = $LOCAL . "." . ($i + 1); my $old = $LOCAL . "." . $i; my $command = "mv $old $new"; debug("Moving directories"); if ( stat($old)){ system("$command") unless $SIMULATE; } } # copy with hard links base folder to .1 my $command = "cp -al " . $LOCAL . " " . $LOCAL . ".1"; debug("Executing: $command\n"); if ( stat($LOCAL)){ system("$command") unless $SIMULATE; } # execute rsync $USER = $USER . "@" if $USER; my $command = "rsync -a -v --delete -e ssh " . $USER . $HOST . ":" . $DIR . " " . $LOCAL; debug("Executing rsync: $command\n"); system("$command") unless $SIMULATE; debug("script is finished, exiting...\n"); exit 0; ################################################## sub usage { print "usage:\n"; print "-h for help\n"; print "-v for verbose ( more output )\n"; print "-d for debug ( even more output)\n"; print "-D for remote directories\n"; print "-H for remote host\n"; print "-l local backup folder\n"; print "-s simulate only , do not execute\n"; print "-u for the remote user\n"; } sub verbose { print "VERBOSE: " . $_[0] if ( $VERBOSE or $DEBUG ); } sub debug { print "DEBUG: " . $_[0] if ( $DEBUG ); } sub verify_host { my $host = $_[0]; my $dir = $_[1]; my $user = $_[2]; $host = $user . "@" . $host if $user; open(SSH,"ssh $host stat $dir |"); while ( my $line = ){ if ( $line =~ /Modify: / ){ close(SSH); return 1; } } close(SSH); return 0; }