File Coverage

blib/lib/App/p5find.pm
Criterion Covered Total %
statement 45 64 70.3
branch 7 18 38.8
condition 5 7 71.4
subroutine 15 19 78.9
pod 0 7 0.0
total 72 115 62.6


line stmt bran cond sub pod time code
1             package App::p5find;
2 4     4   897504 use v5.18;
  4         29  
3 4     4   19 use warnings;
  4         9  
  4         147  
4              
5             our $VERSION = "0.05";
6              
7 4     4   1773 use File::Next;
  4         7470  
  4         122  
8 4     4   1153 use PPI::Document::File;
  4         278134  
  4         137  
9 4     4   2067 use PPIx::QuoteLike;
  4         102919  
  4         145  
10              
11 4     4   34 use Exporter 'import';
  4         7  
  4         2819  
12             our @EXPORT_OK = qw(
13             p5_doc_iterator
14             p5_find_iterator
15             p5_source_file_iterator
16             p5_method_call_iterator
17             print_file_linenum_line
18             iter_each
19             );
20              
21             my %EXCLUDED = (
22             '.git' => 1,
23             '.svn' => 1,
24             'CVS' => 1,
25             'node_modules' => 1, # You won't hide your Perl5 code there, right ?
26             );
27              
28             sub p5_doc_iterator {
29 3     3 0 23243 my (@paths) = @_;
30 3         15 my $files = p5_source_file_iterator(@paths);
31             return sub {
32 11     11   14800 my $f = $files->();
33 11 100       45 return undef unless defined($f);
34 10         60 my $dom = PPI::Document::File->new( $f, readonly => 1 );
35 10         403153 $dom->index_locations;
36 10         87854 return $dom;
37 3         14 };
38             }
39              
40             sub p5_source_file_iterator {
41 5     5 0 9709 my (@paths) = @_;
42             my $files = File::Next::files(
43 16     16   2021 +{ descend_filter => sub { ! $EXCLUDED{$_} } },
44             @paths
45 5         42 );
46             return sub {
47 15     15   33 my $f;
48 15   100     25 do { $f = $files->() } while defined($f) && ! is_perl5_source_file($f);
  23         61  
49 15         39 return $f;
50             }
51 5         676 }
52              
53             sub is_perl5_source_file {
54 22     22 0 1958 my ($file) = @_;
55 22 100       184 return 1 if $file =~ / \.(?: t|p[ml]|pod|comp ) $/xi;
56 8 50       35 return 0 if $file =~ / \. /xi;
57 0 0       0 if (open my $fh, '<', $file) {
58 0         0 my $line = <$fh>;
59 0 0       0 return 1 if $line =~ m{^#!.*perl};
60             }
61 0         0 return 0;
62             }
63              
64             sub print_file_linenum_line {
65 0     0 0 0 my ($file, $to_print) = @_;
66              
67 0         0 my $line_number = 0;
68 0         0 open my $fh, "<", $file;
69 0         0 while (my $line = <$fh>) {
70 0         0 $line_number++;
71 0 0       0 if ( $to_print->{$line_number} ) {
72 0         0 print "${file}:${line_number}:${line}";
73             }
74             }
75 0         0 close($fh);
76             }
77              
78             sub p5_method_call_iterator {
79 2     2 0 14394 my ($doc) = @_;
80              
81             my $arrows = $doc->find(
82             sub {
83 41     41   430 my $op = $_[1];
84 41         124 return 0 unless $op->isa("PPI::Token::Operator") && $op->content eq '->';
85 4         33 my $op_next = $op->snext_sibling or return 0;
86 4         128 return 0 if $op_next->isa("PPI::Structure::Subscript") || $op_next->isa("PPI::Structure::List");
87 2         4 return 1;
88             }
89 2   100     19 ) || [];
90              
91             return sub {
92 4 100   4   51 return @$arrows ? shift(@$arrows) : undef;
93 2         36 };
94             }
95              
96             sub p5_find_iterator {
97 0     0 0   my ($doc, $cb) = @_;
98 0   0       my $found = $doc->find($cb) || [];
99             return sub {
100 0 0   0     @$found ? shift(@$found) : undef
101             }
102 0           }
103              
104             sub iter_each {
105 0     0 0   my ($iter, $cb) = @_;
106 0           while (my $it = $iter->()) {
107 0 0         last unless defined $cb->($it);
108             }
109             }
110              
111             1;
112              
113             __END__