Skip to content

Instantly share code, notes, and snippets.

@fujieda
Last active December 12, 2015 09:29
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save fujieda/4752425 to your computer and use it in GitHub Desktop.
Save fujieda/4752425 to your computer and use it in GitHub Desktop.
A Perl script to mirror SD card images of Raspberry Pi
#!/usr/bin/env perl
# A script to mirror SD card images of Raspberry Pi
# Licensed under the MIT license: http://fujieda.mit-license.org/2013
use strict;
use HTTP::Tiny;
use HTTP::Date;
use File::Path qw(mkpath);
my $rpi = "raspberrypi";
my $downloads = "http://www.raspberrypi.org/downloads";
my $src = "http://downloads.raspberrypi.org/images/";
my $dst = "/ftp/pub/$rpi/";
my $http = HTTP::Tiny->new();
mkdir("log") unless -d "log";
open(my $log, '>>', "log/$rpi.log") or die "can't open log/$rpi.log: $!\n";
select($log);
print "-- start: ". localtime() ."\n";
if (mirror($src, $dst)) {
open(my $timestamp, '>', "log/$rpi.timestamp") or die "can't open log/$rpi.timestamp: $!\n";
close($timestamp);
}
print "-- end: ". localtime() ."\n";
close($log);
sub mirror
{
my ($src, $dst) = @_;
my $response = $http->get($downloads);
unless ($response->{success}) {
print "$src: $response->{status} $response->{reason}\n";
return undef;
}
for (split("\n", $response->{content})) {
next unless m{<a href="$src((.+/)[^/]+)"};
my ($file, $dir) = ($1, $2);
mkpath("$dst$dir");
return undef unless fetch("$src$file", "$dst$file");
}
return 1;
}
sub fetch
{
my ($src, $dst) = @_;
my %opt;
if (-f $dst) {
my $mtime = (stat(_))[9];
$opt{headers}{"If-Modified-Since"} = time2str($mtime);
}
my $response;
while (1) {
$response = $http->get($src, \%opt);
return 1 if $response->{status} == 304;
unless ($response->{success}) {
print "$src: $response->{status} $response->{reason}\n";
return undef;
}
if ($response->{content} =~ m{(http://files\.velocix\.com/[^"]+)}) {
$src = $1;
next;
}
last;
}
my $mtime = str2time($response->{headers}{"last-modified"});
my $fh;
unless (open($fh, '>', $dst)) {
print("can't open $dst: $!\n");
return undef;
}
print $fh $response->{content};
close($fh);
utime(undef, $mtime, $dst);
print("$dst: transferred.\n");
return 1;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment