Subject: | hash keys called "package" treated as a package declaration. |
I ran into a couple of bugs as a side effect of doing
{ package => 'foo' }
While its perfectly legitimate peel code, perlcritic confuses it.
I then tried disambiguating it with
+{
at the front, and the problem went from bad to worse.
Attached is a test script ( also visible here:
http://gist.github.com/244947 ) that exemplifies the problems I encountered.
Current work around: Quote the hash key explicitly, don't use + to
disambiguate.
Subject: | duplicatePackage.pl |
package duplicatePackage;
# $Id:$
use strict;
use warnings;
use Perl::Critic;
use Test::More;
my @strings = (
q| { package => "", }|, # 0 => Fails
q| +{ package => "", }|, # 1 => Fails
q| { 'package' => "", }|, # 2
q| +{ 'package' => "", }|, # 3 => Fails
q| { 'package' , "", }|, # 4
q| +{ 'package' , "", }|, # 5 => Fails.
);
sub generate_code {
my ( $package, $signature ) = @_;
return sprintf <<'EOF', $package, $signature;
package %s;
use strict;
use warnings;
use Data::Dumper qw( Dumper );
sub subx {
my $foo = [ {}, %s ,];
return $foo;
}
subx();
1;
EOF
}
my $testid = 0;
sub generate_test {
my $id = $testid++;
my $signature = shift;
my $package = "Test::Package::_${id}_";
my $code = generate_code( $package, $signature );
return {
id => $id,
package => $package,
code => $code,
signature => $signature,
};
}
my $critic = Perl::Critic->new( -include => [ 'ProhibitCommaSeparatedStatements', 'ProhibitMultiplePackages' ] );
for my $string ( @strings ){
my $testdata = generate_test( $string );
undef $@;
ok( eval $testdata->{code} , 'Evaling the codeblock for test ' . $testdata->{id} . 'works' );
ok( !$@ , 'No Eval errors for ' . $testdata->{id} );
is_deeply( $testdata->{package}->subx() , [ {}, {'package', '' }], 'Data structure is solid for ' . $testdata->{id} );
my @violations = $critic->critique( \$testdata->{code});
ok( !@violations , 'Violations is empty for ' . $testdata->{id} ) or diag explain { test => $testdata, violations => "@violations" };
}
1;