#!/usr/bin/perl -w # bload - easy upload for web files # by Eiki Martinson # Makes a checksum file (using MD5) of all files in the directory. Each time bload is # run, it will compare current checksums against this file; any differences indicate # the file has been changed and needs to be uploaded again. This it will do using scp # with parameters provided by constants. use strict; use Digest::MD5 qw(md5_hex); use System2; use constant CHECK_FILE => ".blcheck"; use constant SERVERNAME => "foo.bar.baz"; use constant SERVERPATH => "www/"; #something like "web/" or "files/" use constant SERVERUSER => "myname"; #your username my $file; my $contents; my @line; my @null = split(/\//, `pwd`); my $localdir = pop(@null); chop($localdir); my $allfiles = `ls -R1Bp | grep -v .*\\/\$`; my @dirs = split(/\s+\.\//, $allfiles); foreach(@dirs) { my %oldchecksums; my %newchecksums; my ($path, @files) = split(/\n/); if($path eq '.:') { $path = ''; } else { $path =~ s/(.*):$/$1\//; } my $remotepath = $localdir."/".$path; #if checksum file already exists, compare checksums and update as necessary if(-e $path.CHECK_FILE) { #get old checksums from the file open(CHECK, "<$path".CHECK_FILE); while() { chomp; @line = split(/\s/); #filename as hash key, digest as value $oldchecksums{$line[0]} = $line[1]; } close(CHECK); #make new md5 digests from actual files, compare, and upload if different foreach $file (@files) { my $newsum = file_md5($path, $file); if(!($oldchecksums{$file}) || $newsum ne $oldchecksums{$file}) { update($path, $file, $remotepath); $newchecksums{$file} = $newsum; } else { $newchecksums{$file} = $oldchecksums{$file}; } } #write new checksums to file open(CHECK, ">$path".CHECK_FILE); while(@line = each %newchecksums) { print CHECK "$line[0] $line[1]\n"; } close(CHECK); } #otherwise generate the checksum file from scratch else { open(CHECK, ">$path".CHECK_FILE); foreach $file (@files) { update($remotepath, $file); print CHECK "$file ".file_md5($path, $file)."\n"; } close(CHECK); } } #make md5 digest from file contents. sub file_md5 { open(FILE, $_[0].$_[1]); my @lines = ; close(FILE); my $contents; foreach(@lines) { $contents = $contents.$_; } return md5_hex($contents); } #upload file sub update { print "Uploading $_[0]"."$_[1]\n"; my ($out, $err) = system2('scp', $_[0].$_[1], SERVERUSER.'@'.SERVERNAME.':'.SERVERPATH.$_[2].$_[1]); if($err) { die "$err File $file was not uploaded. Please try again.\n"; } }