Hi all,
I've implemented a (rather rough) hack in our build subclass which
allows different testfile extensions to be mapped to test<foo> tags.
In this case, testgui will run any *.gt files found (recursively) in the
t/ directory.
testfile_types => {
'gui' => 'gt',
},
Additionally, the "testall" action will run all of the test types. I
would like to not have to explicitly define ACTION_testgui(), but for
now I would like some feedback on whether this is a desirable feature
and/or thoughts on a cleaner implementation or any glaring issues.
The implementation is primarily in transforming ACTION_test() into the
generic_test() method, which takes a 'type' argument.
sub ACTION_testgui {
my $self = shift;
$self->generic_test(type => 'gui');
}
sub ACTION_testall {
my $self = shift;
my $p = $self->{properties};
my @test_types = ('t',
($p->{testfile_types} ? keys(%{$p->{testfile_types}}) : ())
);
$self->generic_test(types => [EMAIL PROTECTED]);
}
I seem to recall a few discussions about "author tests" and such, so it
seems like there might be some interest in such a feature. Perhaps
"testnetwork", "testserver", "testdisk", etc. might be useful for
things that require explicit environment/setup?
Below is some code forked out of Module::Build::Base, which is used to
enable the above behavior. ATM, I've just written this into our build
subclass, but would be happy to make it a patch if there's interest.
Thanks,
Eric
sub ACTION_test {
my $self = shift;
$self->generic_test(type => 't');
}
# stolen from M::B::B::ACTION_test
sub generic_test {
my $self = shift;
(@_ % 2) and
croak('Odd number of elements in argument hash');
my %args = @_;
my @types = (
(exists($args{type}) ? $args{type} : ()),
(exists($args{types}) ? @{$args{types}} : ()),
);
@types or croak "need some types of tests to check";
my $p = $self->{properties};
require Test::Harness;
$self->depends_on('code');
# Do everything in our power to work with all
# versions of Test::Harness
my @harness_switches = $p->{debugger} ? qw(-w -d) : ();
local $Test::Harness::switches =
join ' ', grep defined, $Test::Harness::switches, @harness_switches;
local $Test::Harness::Switches =
join ' ', grep defined, $Test::Harness::Switches, @harness_switches;
local $ENV{HARNESS_PERL_SWITCHES} =
join ' ', grep defined, $ENV{HARNESS_PERL_SWITCHES},
@harness_switches;
$Test::Harness::switches = undef
unless length $Test::Harness::switches;
$Test::Harness::Switches = undef
unless length $Test::Harness::Switches;
delete $ENV{HARNESS_PERL_SWITCHES}
unless length $ENV{HARNESS_PERL_SWITCHES};
local ($Test::Harness::verbose,
$Test::Harness::Verbose,
$ENV{TEST_VERBOSE},
$ENV{HARNESS_VERBOSE}) = ($p->{verbose} || 0) x 4;
# Make sure we test the module in blib/
local @INC = (File::Spec->catdir($p->{base_dir}, $self->blib, 'lib'),
File::Spec->catdir($p->{base_dir}, $self->blib, 'arch'),
@INC);
# Filter out nonsensical @INC entries - some versions of
# Test::Harness will really explode the number of entries here
@INC = grep {ref() || -d} @INC if @INC > 100;
my $tests = $self->find_test_files(@types);
if (@$tests) {
# Work around a Test::Harness bug that loses the particular perl
# we're running under. $self->perl is trustworthy, but $^X isn't.
local $^X = $self->perl;
Test::Harness::runtests(@$tests);
} else {
$self->log_info("No tests defined.\n");
}
# This will get run and the user will see the output. It doesn't
# emit Test::Harness-style output.
if (-e 'visual.pl') {
$self->run_perl_script('visual.pl', '-Mblib='.$self->blib);
}
}
sub expand_test_dir {
my $self = shift;
my ($dir, @types) = @_;
my $p = $self->{properties};
my @tfiles;
my @typelist;
foreach my $type (@types) {
# old-school
if($type eq 't') { push(@typelist, 't'); next; }
defined($p->{testfile_types}) or
Carp::confess(
"cannot have typed testfiles without 'testfile_types' data");
defined($p->{testfile_types}{$type}) or
croak "no testfile_type '$type' is defined";
push(@typelist, $p->{testfile_types}{$type});
}
#warn "expand_test_dir($dir, @types) @typelist";
#do('./util/BREAK_THIS') or die;
if($self->recursive_test_files) {
push(@tfiles, @{$self->rscan_dir($dir, qr{^[^.].*\.$_$})})
for(@typelist);
}
else {
push(@tfiles, glob(File::Spec->catfile($dir, $_)))
for(map({"*.$_"} @typelist));
}
$p->{verbose} and warn "found ", scalar(@tfiles), " test files\n";
return(sort(@tfiles));
}
sub find_test_files {
my $self = shift;
my (@types) = @_;
my $p = $self->{properties};
if (my $files = $p->{test_files}) {
$files = [keys %$files] if UNIVERSAL::isa($files, 'HASH');
$files = [map { -d $_ ? $self->expand_test_dir($_, @types) : $_ }
map glob,
$self->split_like_shell($files)];
# Always given as a Unix file spec.
return [ map $self->localize_file_path($_), @$files ];
} else {
# Find all possible tests in t/ or test.pl
my @tests;
push @tests, 'test.pl' if -e 'test.pl';
push @tests, $self->expand_test_dir('t', @types) if -e 't' and -d _;
return [EMAIL PROTECTED];
}
}
--
Speak softly and carry a big carrot.
---------------------------------------------------
http://scratchcomputing.com
---------------------------------------------------