diff options
Diffstat (limited to 'perl-external/bin/module-manage.pl')
-rwxr-xr-x | perl-external/bin/module-manage.pl | 159 |
1 files changed, 159 insertions, 0 deletions
diff --git a/perl-external/bin/module-manage.pl b/perl-external/bin/module-manage.pl new file mode 100755 index 000000000..f0defb75c --- /dev/null +++ b/perl-external/bin/module-manage.pl @@ -0,0 +1,159 @@ +#!/usr/bin/env perl + +use strict; +use warnings; + +use IPC::Run3; +use LWP::Simple; +use File::Slurp; +use Path::Class; +use List::MoreUtils 'uniq'; + +my $root_dir = file(__FILE__)->dir->parent->absolute->stringify; +my $module_list = "$root_dir/modules.txt"; +my $url_list = "$root_dir/urls.txt"; +my $minicpan = "$root_dir/minicpan"; + +my %actions = ( + add => \&add, + build_all => \&build_all, + fetch_all => \&fetch_all, + force_install => \&force_install, + index_minicpan => \&index_minicpan, + init => \&init, + setup => \&setup, + sort_files => \&sort_files, + zap => \&zap, +); + +# work out what to run +my ( $action, @args ) = @ARGV; +$actions{$action} + ? $actions{$action}->(@args) + : die "Usage: $0 action [args ...]\n"; + +exit; + +############################################################################ + +sub init { + add('App::cpanminus'); + add('MyCPAN::App::DPAN'); +} + +sub setup { + fetch_all(); + build('App::cpanminus'); + build('MyCPAN::App::DPAN'); + build_all(); +} + +sub add { + my $module = shift || die "Usage: $0 add Dist::To::Add"; + + # try to install the distribution using cpanm + my $out = ''; + my $cmd = "cpanm --reinstall $module"; + + # print " running '$cmd'\n"; + run3( $cmd, undef, \$out, \$out ) + || die "Error running '$cmd'"; + + my @fetched_urls = + map { s{.*(http://\S+).*}{$1}; $_ } + grep { m{^Fetching http://search.cpan.org} } + split /\n/, $out; + + write_file( $module_list, { append => 1 }, "$module\n" ); + write_file( $url_list, { append => 1 }, map { "$_\n" } @fetched_urls ); + sort_files(); + + fetch_all(); + index_minicpan(); + + if ( $out =~ m{FAIL} ) { + die "\n\n\n" + . "ERROR: Something did not build correctly" + . " - please see ~/.cpanm/build_log for details" + . "\n\n\n"; + } +} + +sub index_minicpan { + + # go to the minicpan dir and run dpan there + if ( `which dpan` =~ m/\S/ ) { + chdir $minicpan; + system "dpan -f ../dpan_config"; + } + else { + warn "Skipping indexing - could not find dpan"; + } +} + +sub build_all { + my @modules = sort uniq map { s{\s+$}{}; $_; } read_file($module_list); + build($_) for @modules; +} + +sub build { + my $module = shift # + || die "Usage: $0 build Module::To::Build\n"; + + print " --- installing $module ---\n"; + + my $out = ''; + my $cmd = "cpanm --mirror $minicpan --mirror-only $module"; + + # print " running '$cmd'\n"; + + run3( $cmd, undef, \$out, \$out ) + || die "Error running '$cmd'"; + + my @lines = + grep { m{\S} } + split /\n+/, $out; + my $last_line = $lines[-1]; + + die "Error building '$module':\n\n$last_line\n\n$out\n\n" + unless $last_line =~ m{Successfully installed } + || $last_line =~ m{is up to date} + || $last_line =~ m{\d+ distributions? installed}; +} + +sub fetch_all { + my @urls = sort uniq map { s{\s+$}{}; $_; } read_file($url_list); + fetch($_) for @urls; +} + +sub fetch { + my $url = shift; + my ($filename) = $url =~ m{/(authors/.+)$}; + + my $destination = file("$minicpan/$filename"); + $destination->dir->mkpath; + + return if -e $destination; + + print " Fetching $url\n"; + print " -> $destination\n"; + + is_success( getstore( $url, "$destination" ) ) + || die "Error saving $url to $destination"; +} + +sub zap { + + # delete all the bits that are generated + my $local_lib_root = $ENV{PERL_LOCAL_LIB_ROOT} || die; + dir($local_lib_root)->rmtree(1); + dir($minicpan)->subdir('authors')->rmtree(1); +} + +sub sort_files { + foreach my $file ( $url_list, $module_list ) { + my @entries = read_file($file); + @entries = uniq sort @entries; + write_file( $file, @entries ); + } +}
\ No newline at end of file |