]> git.ipfire.org Git - thirdparty/bugzilla.git/commitdiff
Bug 350220: Add hooks to checksetup for extensions.
authormkanat%bugzilla.org <>
Tue, 17 Oct 2006 13:05:14 +0000 (13:05 +0000)
committermkanat%bugzilla.org <>
Tue, 17 Oct 2006 13:05:14 +0000 (13:05 +0000)
Patch By Max Kanat-Alexander <mkanat@bugzilla.org> r=ghendricks, a=myk

Bugzilla/Hook.pm
Bugzilla/Install/Requirements.pm

index be4a70077ca600a56f0b0c31b9eef35f3366f810..f8167cd650966545190e1b764955dd30b22ef136 100644 (file)
@@ -139,6 +139,30 @@ Params:
 
 =back
 
+=head2 install-requirements
+
+Because of the way Bugzilla installation works, there can't be a normal
+hook during the time that F<checksetup.pl> checks what modules are
+installed. (C<Bugzilla::Hook> needs to have those modules installed--it's
+a chicken-and-egg problem.)
+
+So instead of the way hooks normally work, this hook just looks for two 
+subroutines (or constants, since all constants are just subroutines) in 
+your file, called C<OPTIONAL_MODULES> and C<REQUIRED_MODULES>,
+which should return arrayrefs in the same format as C<OPTIONAL_MODULES> and
+C<REQUIRED_MODULES> in L<Bugzilla::Install::Requirements>.
+
+These subroutines will be passed an arrayref that contains the current
+Bugzilla requirements of the same type, in case you want to modify
+Bugzilla's requirements somehow. (Probably the most common would be to
+alter a version number or the "feature" element of C<OPTIONAL_MODULES>.)
+
+F<checksetup.pl> will add these requirements to its own.
+
+Please remember--if you put something in C<REQUIRED_MODULES>, then
+F<checksetup.pl> B<cannot complete> unless the user has that module
+installed! So use C<OPTIONAL_MODULES> whenever you can.
+
 =head2 install-update_db
 
 This happens at the very end of all the tables being updated
index f9bcc971145c62fe4f187fd6afff9dee19b75dfb..14efd15f484fedc2eec7b9160b42f021b453d45a 100644 (file)
@@ -27,6 +27,7 @@ use strict;
 
 use List::Util qw(max);
 use POSIX ();
+use Safe;
 
 use base qw(Exporter);
 our @EXPORT = qw(
@@ -43,11 +44,15 @@ our @EXPORT = qw(
 
 use Bugzilla::Constants;
 
+# The below two constants are subroutines so that they can implement
+# a hook. Other than that they are actually constants.
+
 # "package" is the perl package we're checking for. "module" is the name
 # of the actual module we load with "require" to see if the package is
 # installed or not. "version" is the version we need, or 0 if we'll accept
 # any version.
-use constant REQUIRED_MODULES => [
+sub REQUIRED_MODULES {
+    my @modules = (
     {
         package => 'CGI',
         module  => 'CGI',
@@ -89,9 +94,15 @@ use constant REQUIRED_MODULES => [
         module  => ON_WINDOWS ? 'MIME::Tools' : 'MIME::Parser',
         version => '5.406'
     },
-];
+    );
+
+    my $all_modules = _get_extension_requirements(
+        'REQUIRED_MODULES', \@modules);
+    return $all_modules;
+};
 
-use constant OPTIONAL_MODULES => [
+sub OPTIONAL_MODULES {
+    my @modules = (
     {
         package => 'GD',
         module  => 'GD',
@@ -194,7 +205,39 @@ use constant OPTIONAL_MODULES => [
         version => '0.96',
         feature => 'mod_perl'
     },
-];
+    );
+
+    my $all_modules = _get_extension_requirements(
+        'OPTIONAL_MODULES', \@modules);
+    return $all_modules;
+};
+
+# This implements the install-requirements hook described in Bugzilla::Hook.
+sub _get_extension_requirements {
+    my ($function, $base_modules) = @_;
+    my @all_modules;
+    # get a list of all extensions
+    my @extensions = glob(bz_locations()->{'extensionsdir'} . "/*");
+    foreach my $extension (@extensions) {
+        my $file = "$extension/code/install-requirements.pl";
+        if (-e $file) {
+            my $safe = new Safe;
+            # This is a very liberal Safe.
+            $safe->permit(qw(:browse require entereval caller));
+            $safe->rdo($file);
+            if ($@) {
+                warn $@;
+                next;
+            }
+            my $modules = eval { &{$safe->varglob($function)}($base_modules) };
+            next unless $modules;
+            push(@all_modules, @$modules);
+        }
+    }
+
+    unshift(@all_modules, @$base_modules);
+    return \@all_modules;
+};
 
 sub check_requirements {
     my ($output) = @_;