From 2c33712dc066463ab9741a009e56d9a5c2ffedf6 Mon Sep 17 00:00:00 2001 From: Dylan Hardison Date: Tue, 23 Feb 2016 16:23:20 -0500 Subject: Bug 1246528 - Use Makefile.PL and allow Bugzilla use cpanm-compatible local dependencies r=dkl,a=dylan --- Bugzilla/Install/CPAN.pm | 339 ----------------------------------------------- 1 file changed, 339 deletions(-) delete mode 100644 Bugzilla/Install/CPAN.pm (limited to 'Bugzilla/Install/CPAN.pm') diff --git a/Bugzilla/Install/CPAN.pm b/Bugzilla/Install/CPAN.pm deleted file mode 100644 index 094784e1a..000000000 --- a/Bugzilla/Install/CPAN.pm +++ /dev/null @@ -1,339 +0,0 @@ -# This Source Code Form is subject to the terms of the Mozilla Public -# License, v. 2.0. If a copy of the MPL was not distributed with this -# file, You can obtain one at http://mozilla.org/MPL/2.0/. -# -# This Source Code Form is "Incompatible With Secondary Licenses", as -# defined by the Mozilla Public License, v. 2.0. - -package Bugzilla::Install::CPAN; - -use 5.10.1; -use strict; -use warnings; - -use parent qw(Exporter); -our @EXPORT = qw( - BZ_LIB - - check_cpan_requirements - set_cpan_config - install_module -); - -use Bugzilla::Constants; -use Bugzilla::Install::Requirements qw(have_vers); -use Bugzilla::Install::Util qw(bin_loc install_string); - -use Config; -use CPAN; -use Cwd qw(abs_path); -use File::Path qw(rmtree); - -# These are required for install-module.pl to be able to install -# all modules properly. -use constant REQUIREMENTS => ( - { - module => 'CPAN', - package => 'CPAN', - version => '1.81', - }, - { - # When Module::Build isn't installed, the YAML module allows - # CPAN to read META.yml to determine that Module::Build first - # needs to be installed to compile a module. - module => 'YAML', - package => 'YAML', - version => 0, - }, - { - # Many modules on CPAN are now built with Dist::Zilla, which - # unfortunately means they require this version of EU::MM to install. - module => 'ExtUtils::MakeMaker', - package => 'ExtUtils-MakeMaker', - version => '6.31', - }, -); - -# We need the absolute path of ext_libpath, because CPAN chdirs around -# and so we can't use a relative directory. -# -# We need it often enough (and at compile time, in install-module.pl) so -# we make it a constant. -use constant BZ_LIB => abs_path(bz_locations()->{ext_libpath}); - -# CPAN requires nearly all of its parameters to be set, or it will start -# asking questions to the user. We want to avoid that, so we have -# defaults here for most of the required parameters we know about, in case -# any of them aren't set. The rest are handled by set_cpan_defaults(). -use constant CPAN_DEFAULTS => { - auto_commit => 0, - # We always force builds, so there's no reason to cache them. - build_cache => 0, - build_requires_install_policy => 'yes', - cache_metadata => 1, - colorize_output => 1, - colorize_print => 'bold', - index_expire => 1, - scan_cache => 'atstart', - - inhibit_startup_message => 1, - - bzip2 => bin_loc('bzip2'), - curl => bin_loc('curl'), - gzip => bin_loc('gzip'), - links => bin_loc('links'), - lynx => bin_loc('lynx'), - make => bin_loc('make'), - pager => bin_loc('less'), - tar => bin_loc('tar'), - unzip => bin_loc('unzip'), - wget => bin_loc('wget'), - - urllist => ['http://www.cpan.org/'], -}; - -sub check_cpan_requirements { - my ($original_dir, $original_args) = @_; - - _require_compiler(); - - my @install; - foreach my $module (REQUIREMENTS) { - my $installed = have_vers($module, 1); - push(@install, $module) if !$installed; - } - - return if !@install; - - my $restart_required; - foreach my $module (@install) { - $restart_required = 1 if $module->{module} eq 'CPAN'; - install_module($module->{module}, 1); - } - - if ($restart_required) { - chdir $original_dir; - exec($^X, $0, @$original_args); - } -} - -sub _require_compiler { - my @errors; - - my $cc_name = $Config{cc}; - my $cc_exists = bin_loc($cc_name); - - if (!$cc_exists) { - push(@errors, install_string('install_no_compiler')); - } - - my $make_name = $CPAN::Config->{make}; - my $make_exists = bin_loc($make_name); - - if (!$make_exists) { - push(@errors, install_string('install_no_make')); - } - - die @errors if @errors; -} - -sub install_module { - my ($name, $test) = @_; - my $bzlib = BZ_LIB; - - # Make Module::AutoInstall install all dependencies and never prompt. - local $ENV{PERL_AUTOINSTALL} = '--alldeps'; - # This makes Net::SSLeay not prompt the user, if it gets installed. - # It also makes any other MakeMaker prompts accept their defaults. - local $ENV{PERL_MM_USE_DEFAULT} = 1; - - # Certain modules require special stuff in order to not prompt us. - my $original_makepl = $CPAN::Config->{makepl_arg}; - # This one's a regex in case we're doing Template::Plugin::GD and it - # pulls in Template-Toolkit as a dependency. - if ($name =~ /^Template/) { - $CPAN::Config->{makepl_arg} .= " TT_ACCEPT=y TT_EXTRAS=n"; - } - elsif ($name eq 'XML::Twig') { - $CPAN::Config->{makepl_arg} = "-n $original_makepl"; - } - elsif ($name eq 'SOAP::Lite') { - $CPAN::Config->{makepl_arg} .= " --noprompt"; - } - - my $module = CPAN::Shell->expand('Module', $name); - if (!$module) { - die install_string('no_such_module', { module => $name }) . "\n"; - } - - print install_string('install_module', - { module => $name, version => $module->cpan_version }) . "\n"; - - if ($test) { - CPAN::Shell->force('install', $name); - } - else { - CPAN::Shell->notest('install', $name); - } - - # If it installed any binaries in the Bugzilla directory, delete them. - if (-d "$bzlib/bin") { - File::Path::rmtree("$bzlib/bin"); - } - - $CPAN::Config->{makepl_arg} = $original_makepl; -} - -sub set_cpan_config { - my $do_global = shift; - my $bzlib = BZ_LIB; - - # We set defaults before we do anything, otherwise CPAN will - # start asking us questions as soon as we load its configuration. - eval { require CPAN::Config; }; - _set_cpan_defaults(); - - # Calling a senseless autoload that does nothing makes us - # automatically load any existing configuration. - # We want to avoid the "invalid command" message. - open(my $saveout, ">&", "STDOUT"); - open(STDOUT, '>', '/dev/null'); - eval { CPAN->ignore_this_error_message_from_bugzilla; }; - undef $@; - close(STDOUT); - open(STDOUT, '>&', $saveout); - - my $dir = $CPAN::Config->{cpan_home}; - if (!defined $dir || !-w $dir) { - # If we can't use the standard CPAN build dir, we try to make one. - $dir = "$ENV{HOME}/.cpan"; - mkdir $dir; - - # If we can't make one, we finally try to use the Bugzilla directory. - if (!-w $dir) { - print STDERR install_string('cpan_bugzilla_home'), "\n"; - $dir = "$bzlib/.cpan"; - } - } - $CPAN::Config->{cpan_home} = $dir; - $CPAN::Config->{build_dir} = "$dir/build"; - # We always force builds, so there's no reason to cache them. - $CPAN::Config->{keep_source_where} = "$dir/source"; - # This is set both here and in defaults so that it's always true. - $CPAN::Config->{inhibit_startup_message} = 1; - # Automatically install dependencies. - $CPAN::Config->{prerequisites_policy} = 'follow'; - - # Unless specified, we install the modules into the Bugzilla directory. - if (!$do_global) { - require Config; - - $CPAN::Config->{makepl_arg} .= " LIB=\"$bzlib\"" - . " INSTALLMAN1DIR=\"$bzlib/man/man1\"" - . " INSTALLMAN3DIR=\"$bzlib/man/man3\"" - # The bindirs are here because otherwise we'll try to write to - # the system binary dirs, and that will cause CPAN to die. - . " INSTALLBIN=\"$bzlib/bin\"" - . " INSTALLSCRIPT=\"$bzlib/bin\"" - # INSTALLDIRS=perl is set because that makes sure that MakeMaker - # always uses the directories we've specified here. - . " INSTALLDIRS=perl"; - $CPAN::Config->{mbuild_arg} = " --install_base \"$bzlib\"" - . " --install_path lib=\"$bzlib\"" - . " --install_path arch=\"$bzlib/$Config::Config{archname}\""; - $CPAN::Config->{mbuild_install_arg} = $CPAN::Config->{mbuild_arg}; - - # When we're not root, sometimes newer versions of CPAN will - # try to read/modify things that belong to root, unless we set - # certain config variables. - $CPAN::Config->{histfile} = "$dir/histfile"; - $CPAN::Config->{use_sqlite} = 0; - $CPAN::Config->{prefs_dir} = "$dir/prefs"; - - # Unless we actually set PERL5LIB, some modules can't install - # themselves, like DBD::mysql, DBD::Pg, and XML::Twig. - my $current_lib = $ENV{PERL5LIB} ? $ENV{PERL5LIB} . ':' : ''; - $ENV{PERL5LIB} = $current_lib . $bzlib; - } -} - -sub _set_cpan_defaults { - # If CPAN hasn't been configured, we try to use some reasonable defaults. - foreach my $key (keys %{CPAN_DEFAULTS()}) { - $CPAN::Config->{$key} = CPAN_DEFAULTS->{$key} - if !defined $CPAN::Config->{$key}; - } - - my @missing; - # In newer CPANs, this is in HandleConfig. In older CPANs, it's in - # Config. - if (eval { require CPAN::HandleConfig }) { - @missing = CPAN::HandleConfig->missing_config_data; - } - else { - @missing = CPAN::Config->missing_config_data; - } - - foreach my $key (@missing) { - $CPAN::Config->{$key} = ''; - } -} - -1; - -__END__ - -=head1 NAME - -Bugzilla::Install::CPAN - Routines to install Perl modules from CPAN. - -=head1 SYNOPSIS - - use Bugzilla::Install::CPAN; - - set_cpan_config(); - install_module('Module::Name'); - -=head1 DESCRIPTION - -This is primarily used by L to do the "hard work" of -installing CPAN modules. - -=head1 SUBROUTINES - -=over - -=item C - -Sets up the configuration of CPAN for this session. Must be called -before L. Takes one boolean parameter. If true, -L will install modules globally instead of to the -local F directory. On most systems, you have to be root to do that. - -=item C - -Installs a module from CPAN. Takes two arguments: - -=over - -=item C<$name> - The name of the module, just like you'd pass to the -C command in the CPAN shell. - -=item C<$test> - If true, we run tests on this module before installing, -but we still force the install if the tests fail. This is only used -when we internally install a newer CPAN module. - -=back - -Note that calling this function prints a B of information to -STDOUT and STDERR. - -=back - -=head1 B - -=over - -=item check_cpan_requirements - -=back -- cgit v1.2.3-24-g4f1b