DB-Handy

 view release on metacpan or  search on metacpan

t/lib/INA_CPAN_Check.pm  view on Meta::CPAN

        $top_entry = $line;
        last;
    }
    ok($top_entry =~ /^\d+\.\d+\S*\s+\d{4}-\d{2}-\d{2}/
    || $top_entry =~ /^\d+\.\d+\S*\s+\d{4}-\d{2}/
    || $top_entry =~ /^\d+\.\d+\S*\s+\S+/,
       "H - latest Changes entry has VERSION + DATE format: '$top_entry'");

    my $has_body = 0;
    my $in_entry = 0;
    for my $line (@lines) {
        $line =~ s/\r?\n$//;
        if ($line =~ /^\d+\.\d+/) { $in_entry = 1; next }
        if ($in_entry && $line =~ /^\s+\S/) { $has_body = 1; last }
        last if $in_entry && $line =~ /^\d+\.\d+/;
    }
    ok($has_body, 'H - latest Changes entry has indented description body');
}

sub count_H { return 3 }

######################################################################
# Category I: Makefile.PL
######################################################################

sub check_I {
    my ($root) = @_;
    my $text = _slurp("$root/Makefile.PL");
    ok($text =~ /WriteMakefile\s*\(/, 'I - Makefile.PL calls WriteMakefile()');
    ok($text =~ /'NAME'/ && $text =~ /'VERSION'/,
       'I - Makefile.PL contains NAME and VERSION keys');
    ok($text =~ /ina\@cpan\.org/, 'I - Makefile.PL AUTHOR contains ina@cpan.org');
}

sub count_I { return 3 }

######################################################################
# Category J: Consistency
# Accepts optional overrides:
#   j2_stale => [ list of stale strings to check for ]
######################################################################

sub check_J {
    my ($root, %opt) = @_;
    my @manifest = _manifest_files($root);
    my @pm_files = sort grep { /^lib\/.*\.pm$/ && -f "$root/$_" } @manifest;
    my @t_files  = sort grep { /\.t$/  && -f "$root/$_" } @manifest;
    my $meta_yml = _slurp("$root/META.yml");

    # J1: no PREREQ_PM dep version equals module VERSION
    my $pm_ver = _pm_version("$root/$pm_files[0]") if @pm_files;
    my $j1 = 1;
    if ($meta_yml =~ /^requires:(.*?)(?=^\S)/ms) {
        my $block = $1;
        while ($block =~ /:\s*([\d._]+)/g) {
            if (defined $pm_ver && $1 eq $pm_ver) { $j1 = 0; last }
        }
    }
    ok($j1, 'J - PREREQ_PM: no core dep version equals module VERSION');

    # J2: BUGS AND LIMITATIONS has no stale entries
    my @stale = exists $opt{j2_stale} ? @{$opt{j2_stale}} : ();
    my $bugs_text = '';
    if (@pm_files) {
        my $pm_text = _slurp("$root/$pm_files[0]");
        if ($pm_text =~ /=head1 BUGS AND LIMITATIONS(.*?)^=head1/ms) {
            $bugs_text = $1;
        }
    }
    my $j2 = 1;
    for my $entry (@stale) {
        if (index($bugs_text, $entry) >= 0) { $j2 = 0; last }
    }
    ok($j2, 'J - BUGS AND LIMITATIONS: no stale removed-feature entries');

    # J3+J4: test file plan vs ok-comment count
    for my $tf (@t_files) {
        my @lines = _slurp_lines("$root/$tf");
        my @ok_comments;
        my $plan = undef;
        for my $line (@lines) {
            $line =~ s/\r?\n$//;
            push @ok_comments, $1 if $line =~ /^#\s+ok\s+(\d+)\b/;
            $plan = $1 if !defined $plan && $line =~ /^1\.\.(\d+)$/;
        }
        my %seen;
        my $unique = !grep { $seen{$_}++ } @ok_comments;
        ok($unique, "J - $tf: # ok N comments are unique");
        if (defined $plan) {
            ok(scalar(@ok_comments) <= $plan,
               "J - $tf: # ok comment count(" . scalar(@ok_comments) .
               ") does not exceed plan($plan)");
        }
        else {
            ok(1, "J - $tf: no plan line (skip/dynamic)");
        }
    }
}

sub count_J {
    my ($root) = @_;
    my @manifest = _manifest_files($root);
    my @t_files  = grep { /\.t$/ && -f "$root/$_" } @manifest;
    return 1 + 1 + 2 * scalar(@t_files);
}

######################################################################
# Category K: Coding Style
# Accepts optional overrides:
#   k3_exempt => 'regex-alternation-string'  (e.g. 'sch\b|outer_row\b')
######################################################################

sub check_K {
    my ($root, %opt) = @_;
    my @manifest = _manifest_files($root);
    my @pm_files = sort grep { /^lib\/.*\.pm$/ && -f "$root/$_" } @manifest;
    my $k3_exempt = exists $opt{k3_exempt}
        ? $opt{k3_exempt}
        : 'env\\b|opts\\b|args\\b';

    for my $pm (@pm_files) {
        my $text = _slurp("$root/$pm");
        $text =~ s/\n__END__\b.*\z//s;
        $text =~ s/^=[a-zA-Z].*?^=cut[ \t]*$//msg;
        my @lines = split /\n/, $text;
        my $n = 0;

                        # K1: comma followed by space
        my @k1_bad;
        {
            my $lineno = 0;
            for my $raw_line (split /\n/, $text) {
                $lineno++;
                my $s = $raw_line;



( run in 2.448 seconds using v1.01-cache-2.11-cpan-0bb4e1dffa6 )