X-Git-Url: http://git.shadowcat.co.uk/gitweb/gitweb.cgi?a=blobdiff_plain;f=t%2F54taint.t;h=fbf028666d208626c5248e07377eba6eea4eff8a;hb=07a243ad8f4273317a028eb7a55a8682a713eba3;hp=f54ed93331524d84969b0b116f53d12965421814;hpb=91b0ad0b21a3c167f5ae0ac240322de8b6601058;p=dbsrgits%2FDBIx-Class.git diff --git a/t/54taint.t b/t/54taint.t index f54ed93..fbf0286 100644 --- a/t/54taint.t +++ b/t/54taint.t @@ -1,56 +1,122 @@ -#!perl -T - -# the above line forces Test::Harness into taint-mode +BEGIN { $ENV{DBICTEST_ANFANG_DEFANG} = 1 } use strict; use warnings; +use Config; -use Test::More; +# there is talk of possible perl compilations where -T is fatal or just +# doesn't work. We don't want to have the user deal with that. +BEGIN { unless ($INC{'t/lib/DBICTest/WithTaint.pm'}) { -BEGIN { - eval "require Module::Find;"; - if ($@) { - plan skip_all => 'Could not load Module::Find'; - exit; + if ( $^O eq 'MSWin32' and $^X =~ /\x20/ ) { + print "1..0 # SKIP Running this test on Windows with spaces within the perl executable path (\$^X) is not possible due to https://rt.perl.org/Ticket/Display.html?id=123907\n"; + exit 0; } - else { - plan tests => 7; + + # it is possible the test itself is initially invoked in taint mode + # and with relative paths *and* with a relative $^X and some other + # craziness... in short: just be proactive + require File::Spec; + + if (length $ENV{PATH}) { + ( $ENV{PATH} ) = join ( $Config{path_sep}, + map { length($_) ? File::Spec->rel2abs($_) : () } + split /\Q$Config{path_sep}/, $ENV{PATH} + ) =~ /\A(.+)\z/; } -} -package DBICTest::Taint::Classes; + my ($perl) = $^X =~ /\A(.+)\z/; + + { + local $ENV{PATH} = "/nosuchrootbindir"; + system( $perl => -T => -e => ' + use warnings; + use strict; + eval { my $x = $ENV{PATH} . (kill (0)); 1 } or exit 42; + exit 0; + '); + } + + if ( ($? >> 8) != 42 ) { + print "1..0 # SKIP Your perl does not seem to like/support -T...\n"; + exit 0; + } + + exec( $perl, qw( -I. -Mt::lib::DBICTest::WithTaint -T ), __FILE__ ); +}} + +# When in taint mode, PERL5LIB is ignored (but *not* unset) +# Put it back in INC so that local-lib users can actually +# run this test. Use lib.pm instead of an @INC unshift as +# it will correctly add any arch subdirs encountered + +use lib ( + grep { length } + map { split /\Q$Config{path_sep}\E/, (/^(.*)$/)[0] } # untainting regex + grep { defined } + @ENV{qw(PERL5LIB PERLLIB)} # precedence preserved by lib +); + +# We need to specify 'lib' here as well because even if it was already in +# @INC, the above will have put our local::lib in front of it, so now an +# installed DBIx::Class will take precedence over the one we're trying to test. +# In some cases, prove will have supplied ./lib as an absolute path so it +# doesn't seem worth trying to remove the second copy since it won't hurt +# anything. +use lib qw(t/lib lib); use Test::More; use Test::Exception; +use DBICTest; -use lib qw(t/lib); -use base qw/DBIx::Class::Schema/; +throws_ok ( + sub { $ENV{PATH} . (kill (0)) }, + qr/Insecure dependency in kill/, + 'taint mode active' +) if length $ENV{PATH}; -lives_ok (sub { - __PACKAGE__->load_classes(qw/Manual/); - ok( __PACKAGE__->source('Manual'), 'The Classes::Manual source has been registered' ); - __PACKAGE__->_unregister_source (qw/Manual/); -}, 'Loading classes with explicit load_classes worked in taint mode' ); +{ + package DBICTest::Taint::Classes; -lives_ok (sub { - __PACKAGE__->load_classes(); - ok( __PACKAGE__->source('Auto'), 'The Classes::Auto source has been registered' ); - ok( __PACKAGE__->source('Auto'), 'The Classes::Manual source has been re-registered' ); -}, 'Loading classes with Module::Find/load_classes worked in taint mode' ); + use Test::More; + use Test::Exception; + use base qw/DBIx::Class::Schema/; -package DBICTest::Taint::Namespaces; + lives_ok (sub { + __PACKAGE__->load_classes(qw/Manual/); + ok( __PACKAGE__->source('Manual'), 'The Classes::Manual source has been registered' ); + __PACKAGE__->_unregister_source (qw/Manual/); + }, 'Loading classes with explicit load_classes worked in taint mode' ); -use Test::More; -use Test::Exception; + lives_ok (sub { + __PACKAGE__->load_classes(); + ok( __PACKAGE__->source('Auto'), 'The Classes::Auto source has been registered' ); + ok( __PACKAGE__->source('Auto'), 'The Classes::Manual source has been re-registered' ); + }, 'Loading classes with Module::Find/load_classes worked in taint mode' ); +} -use lib qw(t/lib); -use base qw/DBIx::Class::Schema/; +{ + package DBICTest::Taint::Namespaces; -lives_ok (sub { - __PACKAGE__->load_namespaces(); - ok( __PACKAGE__->source('Test'), 'The Namespaces::Test source has been registered' ); -}, 'Loading classes with Module::Find/load_namespaces worked in taint mode' ); + use Test::More; + use Test::Exception; + use base qw/DBIx::Class::Schema/; + + lives_ok (sub { + __PACKAGE__->load_namespaces(); + ok( __PACKAGE__->source('Test'), 'The Namespaces::Test source has been registered' ); + }, 'Loading classes with Module::Find/load_namespaces worked in taint mode' ); +} + +# check that we can create a database and all +{ + my $s = DBICTest->init_schema( sqlite_use_file => 1 ); + my $art = $s->resultset('Artist')->search({}, { + prefetch => 'cds', order_by => 'artistid', + })->next; + is ($art->artistid, 1, 'got artist'); +} -1; +done_testing;