258 lines
7.1 KiB
Perl
258 lines
7.1 KiB
Perl
# Licensed to the Apache Software Foundation (ASF) under one or more
|
|
# contributor license agreements. See the NOTICE file distributed with
|
|
# this work for additional information regarding copyright ownership.
|
|
# The ASF licenses this file to You under the Apache License, Version 2.0
|
|
# (the "License"); you may not use this file except in compliance with
|
|
# the License. You may obtain a copy of the License at
|
|
#
|
|
# http://www.apache.org/licenses/LICENSE-2.0
|
|
#
|
|
# Unless required by applicable law or agreed to in writing, software
|
|
# distributed under the License is distributed on an "AS IS" BASIS,
|
|
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
# See the License for the specific language governing permissions and
|
|
# limitations under the License.
|
|
#
|
|
package Apache::TestMM;
|
|
|
|
use strict;
|
|
use warnings FATAL => 'all';
|
|
|
|
use Config;
|
|
use Apache::TestConfig ();
|
|
use Apache::TestTrace;
|
|
use Apache::TestSmoke;
|
|
|
|
sub import {
|
|
my $class = shift;
|
|
|
|
for my $section (@_) {
|
|
unless (defined &$section) {
|
|
die "unknown Apache::TestMM section: $section";
|
|
}
|
|
no strict 'refs';
|
|
my $sub = "MY::$section";
|
|
# Force aliasing, since previous WriteMakefile might have
|
|
# moved it
|
|
undef &$sub if defined &$sub;
|
|
*$sub = \&{$section};
|
|
}
|
|
}
|
|
|
|
sub add_dep {
|
|
my($string, $targ, $add) = @_;
|
|
$$string =~ s/($targ\s+::)/$1 $add /;
|
|
}
|
|
|
|
sub clean {
|
|
my $self = shift;
|
|
my $string = $self->MM::clean(@_);
|
|
add_dep(\$string, clean => 'test_clean');
|
|
$string;
|
|
}
|
|
|
|
sub test {
|
|
my $self = shift;
|
|
my $env = Apache::TestConfig->passenv_makestr();
|
|
|
|
my $tests = "TEST_FILES =\n";
|
|
|
|
if (ref $self && exists $self->{'test'}) {
|
|
$tests = 'TEST_FILES = ' . $self->{'test'}->{'TESTS'} . "\n";
|
|
}
|
|
|
|
my $preamble = Apache::TestConfig::WIN32 ? "" : <<EOF;
|
|
PASSENV = $env
|
|
EOF
|
|
|
|
my $cover;
|
|
|
|
if (eval { require Devel::Cover }) {
|
|
my $atdir = File::Spec->catfile($ENV{HOME}, '.apache-test');
|
|
|
|
my $cover_exec = Apache::TestConfig::which("cover");
|
|
|
|
my @cover = ("", "testcover :", );
|
|
push @cover, "\t-\@$cover_exec -delete" if $cover_exec;
|
|
push @cover, "\t-HARNESS_PERL_SWITCHES=-MDevel::Cover=+inc,$atdir \\",
|
|
"\tAPACHE_TEST_EXTRA_ARGS=-one-process \$(MAKE) test";
|
|
push @cover, "\t-\@$cover_exec" if $cover_exec;
|
|
$cover = join "\n", @cover, "";
|
|
}
|
|
else {
|
|
|
|
$cover = <<'EOF';
|
|
|
|
testcover :
|
|
@echo "Cannot run testcover action unless Devel::Cover is installed"
|
|
@echo "Don't forget to rebuild your Makefile after installing Devel::Cover"
|
|
EOF
|
|
}
|
|
|
|
return $preamble . $tests . <<'EOF' . $cover;
|
|
TEST_VERBOSE = 0
|
|
|
|
test_clean :
|
|
$(FULLPERL) -I$(INST_ARCHLIB) -I$(INST_LIB) \
|
|
t/TEST $(APACHE_TEST_EXTRA_ARGS) -clean
|
|
|
|
run_tests :
|
|
$(PASSENV) \
|
|
$(FULLPERL) -I$(INST_ARCHLIB) -I$(INST_LIB) \
|
|
t/TEST $(APACHE_TEST_EXTRA_ARGS) -bugreport -verbose=$(TEST_VERBOSE) $(TEST_FILES)
|
|
|
|
test :: pure_all test_clean run_tests
|
|
|
|
test_config :
|
|
$(PASSENV) \
|
|
$(FULLPERL) -I$(INST_ARCHLIB) -I$(INST_LIB) \
|
|
t/TEST $(APACHE_TEST_EXTRA_ARGS) -conf
|
|
|
|
cmodules: test_config
|
|
cd c-modules && $(MAKE) all
|
|
|
|
cmodules_clean: test_config
|
|
cd c-modules && $(MAKE) clean
|
|
EOF
|
|
|
|
}
|
|
|
|
sub generate_script {
|
|
my $file = shift;
|
|
|
|
unlink $file if -e $file;
|
|
|
|
my $body = "BEGIN { eval { require blib && blib->import; } }\n";
|
|
|
|
my %args = @Apache::TestMM::Argv;
|
|
while (my($k, $v) = each %args) {
|
|
$v =~ s/\|/\\|/g;
|
|
$body .= "\n\$Apache::TestConfig::Argv{'$k'} = q|$v|;\n";
|
|
}
|
|
|
|
my $in = Symbol::gensym();
|
|
open $in, "$file.PL" or die "Couldn't open $file.PL: $!";
|
|
{
|
|
local $/;
|
|
$body .= <$in>;
|
|
}
|
|
close $in;
|
|
|
|
info "generating script $file";
|
|
Apache::Test::basic_config()->write_perlscript($file, $body);
|
|
Apache::TestSmoke->generate_script;
|
|
}
|
|
|
|
sub filter_args {
|
|
my($argv, $vars) =
|
|
Apache::TestConfig::filter_args(\@ARGV, \%Apache::TestConfig::Usage);
|
|
@ARGV = @$argv;
|
|
@Apache::TestMM::Argv = %$vars;
|
|
}
|
|
|
|
1;
|
|
|
|
=head1 NAME
|
|
|
|
Apache::TestMM - Provide MakeMaker Wrapper Methods
|
|
|
|
=head1 SYNOPSIS
|
|
|
|
require Apache::TestMM;
|
|
|
|
# import MY::test and MY::clean overrides for MM
|
|
Apache::TestMM->import(qw(test clean));
|
|
|
|
# parse command line args
|
|
Apache::TestMM::filter_args();
|
|
|
|
# autogenerate the script
|
|
Apache::TestMM::generate_script('t/TEST');
|
|
|
|
=head1 DESCRIPTION
|
|
|
|
C<Apache::TestMM> provides wrappers for the C<ExtUtils::MakeMaker>
|
|
craft, making it easier to extend the autogenerated F<Makefile> with
|
|
C<Apache::Test>.
|
|
|
|
=head1 FUNCTIONS
|
|
|
|
=head2 C<import>
|
|
|
|
use Apache::TestMM qw(test clean);
|
|
|
|
or:
|
|
|
|
Apache::TestMM->import(qw(test clean));
|
|
|
|
Imports C<MY::> overrides for the default C<ExtUtils::MakeMaker>
|
|
I<test> and I<clean> targets, as if you have defined:
|
|
|
|
sub MY::test {...}
|
|
sub MY::clean {...}
|
|
|
|
in F<Makefile.PL>. C<Apache::TestMM> does this for you so that these Makefile
|
|
targets will run the Apache server and the tests for it, and clean up after
|
|
its mess.
|
|
|
|
=head2 C<filter_args>
|
|
|
|
push @ARGV, '-apxs', $apxs_path;
|
|
Apache::TestMM::filter_args();
|
|
WriteMakefile(...);
|
|
|
|
When C<WriteMakefile()> is called it parses C<@ARGV>, hoping to find
|
|
special options like C<PREFIX=/home/stas/perl>. C<Apache::Test>
|
|
accepts a lot of configuration options of its own. When
|
|
C<Apache::TestMM::filter_args()> is called, it removes any
|
|
C<Apache::Test>-specific options from C<@ARGV> and stores them
|
|
internally, so when C<WriteMakefile()> is called they aren't in
|
|
C<@ARGV> and thus won't be processed by C<WriteMakefile()>.
|
|
|
|
The options can be set when F<Makefile.PL> is called:
|
|
|
|
% perl Makefile.PL -apxs /path/to/apxs
|
|
|
|
Or you can push them manually to C<@ARGV> from the code:
|
|
|
|
push @ARGV, '-apxs', $apxs_path;
|
|
|
|
When:
|
|
|
|
Apache::TestMM::generate_script('t/TEST');
|
|
|
|
is called, C<Apache::Test>-specific options extracted by
|
|
C<Apache::TestMM::filter_args()> are written to the autogenerated
|
|
file. In our example, the autogenerated F<t/TEST> will include:
|
|
|
|
%Apache::TestConfig::Argv = qw(apxs /path/to/apxs);
|
|
|
|
which is going to be used by the C<Apache::Test> runtime.
|
|
|
|
The other frequently used options are: C<-httpd>, telling where to
|
|
find the httpd (usually when the C<-apxs> option is not used),
|
|
C<-libmodperl> to use a specific mod_perl shared object (if your
|
|
mod_perl is built as DSO), C<-maxclients> to change the default number
|
|
of the configured C<MaxClients> directive, C<-port> to start the
|
|
server on a specific port, etc. To get the complete list of available
|
|
configuration options and their purpose and syntax, run:
|
|
|
|
% perl -MApache::TestConfig -le 'Apache::TestConfig::usage()'
|
|
|
|
You may wish to document some of these in your application's F<README>
|
|
file, especially the C<-apxs> and C<-httpd> options.
|
|
|
|
|
|
=head2 C<generate_script>
|
|
|
|
Apache::TestMM::generate_script('t/TEST');
|
|
|
|
C<generate_script()> accepts the name of the script to generate and
|
|
will look for a template with the same name and suffix I<.PL>. So in
|
|
our example it'll look for F<t/TEST.PL>. The autogenerated script
|
|
F<t/TEST> will include the contents of F<t/TEST.PL>, and special
|
|
directives, including any configuration options passed via
|
|
C<L<filter_args()|/C_filter_args_>> called from F<Makefile.PL>, special
|
|
fixup code, etc.
|
|
|
|
=cut
|