File Coverage

blib/lib/App/Midgen/Role/Eval.pm
Criterion Covered Total %
statement 18 139 12.9
branch 0 82 0.0
condition 0 17 0.0
subroutine 6 13 46.1
pod 1 1 100.0
total 25 252 9.9


line stmt bran cond sub pod time code
1             package App::Midgen::Role::Eval;
2              
3 2     2   1009 use constant {NONE => q{}, TWO => 2,};
  2         5  
  2         127  
4 2     2   8 use Moo::Role;
  2         2  
  2         14  
5             requires
6             qw( ppi_document debug verbose format xtest _process_found_modules develop meta2 );
7              
8 2     2   3515 use Try::Tiny;
  2         4  
  2         103  
9 2     2   8 use Data::Printer {caller_info => 1,};
  2         2  
  2         15  
10 2     2   1840 use List::MoreUtils qw(any firstidx);
  2         2  
  2         34  
11              
12             # Load time and dependencies negate execution time
13             # use namespace::clean -except => 'meta';
14              
15             our $VERSION = '0.33_05';
16             $VERSION = eval $VERSION; ## no critic
17              
18             #######
19             # composed method - xtests_eval
20             #######
21             sub xtests_eval {
22 0     0 1   my $self = shift;
23 0   0       my $phase_relationship = shift || NONE;
24              
25 0           my @modules;
26             my @version_strings;
27              
28             #PPI::Document
29             # PPI::Statement::Sub
30             # PPI::Token::Word 'sub'
31             # PPI::Token::Whitespace ' '
32             # PPI::Token::Word '_assert_ssl'
33             # PPI::Token::Whitespace ' '
34             # PPI::Structure::Block { ... }
35             # PPI::Token::Whitespace '\n'
36             # PPI::Token::Whitespace '\t\t'
37             # PPI::Statement
38             # PPI::Token::Word 'eval'
39             # PPI::Token::Whitespace ' '
40             # PPI::Structure::Block { ... }
41             # PPI::Token::Whitespace ' '
42             # PPI::Statement::Include
43             # PPI::Token::Word 'require'
44             # PPI::Token::Whitespace ' '
45             # PPI::Token::Word 'IO::Socket::SSL'
46             # PPI::Token::Structure ';'
47             # PPI::Token::Whitespace ' '
48             # PPI::Statement
49             # PPI::Token::Word 'IO::Socket::SSL'
50             # PPI::Token::Operator '->'
51             # PPI::Token::Word 'VERSION'
52             # PPI::Structure::List ( ... )
53             # PPI::Statement::Expression
54             # PPI::Token::Number::Float '1.44'
55             # PPI::Token::Whitespace ' '
56             # PPI::Token::Structure ';'
57             # PPI::Token::Whitespace '\n'
58              
59             try {
60              
61 0     0     my @chunks3 = @{$self->ppi_document->find('PPI::Statement::Sub')};
  0            
62              
63 0           foreach my $chunk (@chunks3) {
64 0 0         if (
65             $chunk->find(
66             sub {
67 0 0         $_[1]->isa('PPI::Token::Word')
68             and $_[1]->content =~ m{\A(?:sub)\z};
69             }
70             )
71             )
72             {
73 0           my $module_name;
74             my $version_string;
75 0           for (0 .. $#{$chunk->{children}}) {
  0            
76 0 0         if ($chunk->{children}[$_]->isa('PPI::Structure::Block')) {
77             my $ppi_sb = $chunk->{children}[$_]
78 0 0         if $chunk->{children}[$_]->isa('PPI::Structure::Block');
79 0           for (0 .. $#{$ppi_sb->{children}}) {
  0            
80 0 0         if ($ppi_sb->{children}[$_]->isa('PPI::Statement')) {
81             my $ppi_s = $ppi_sb->{children}[$_]
82 0 0         if $ppi_sb->{children}[$_]->isa('PPI::Statement');
83 0           my @chunks3 = @{$ppi_s->{children}};
  0            
84 0 0         if (
85             any {
86 0 0         $_->isa('PPI::Token::Word')
87             and $_->content =~ m{\A(?:eval|try)\z};
88             }
89 0           @{$ppi_s->{children}}
90             )
91             {
92             my @ppisb = firstidx {
93 0           $_->isa('PPI::Structure::Block');
94             }
95 0           @{$ppi_s->{children}};
  0            
96              
97             # extract first Structure::Block
98 0           my $ppi_sb = $ppisb[0];
99              
100 0           $self->_eval_info($ppi_sb, \$module_name, \$version_string);
101              
102 0 0         print "Option3 $module_name - $version_string\n"
103             if $self->debug;
104              
105              
106 0 0         if (version::is_lax($version_string)) {
107              
108 0           push @modules, $module_name;
109 0 0         $version_string
110             = version::is_lax($version_string)
111             ? $version_string
112             : 0;
113 0           push @version_strings, $version_string;
114 0           $self->{found_version}{$module_name} = $version_string;
115             }
116             }
117             }
118             }
119             }
120             }
121             }
122             }
123 0           };
124              
125              
126             #PPI::Document
127             # PPI::Statement
128             # PPI::Token::Word 'eval'
129             # PPI::Token::Whitespace ' '
130             # PPI::Structure::Block { ... }
131             # PPI::Statement::Include
132             # PPI::Token::Word 'require'
133             # PPI::Token::Whitespace ' '
134             # PPI::Token::Word 'PAR::Dist'
135             # PPI::Token::Structure ';'
136             # PPI::Token::Whitespace ' '
137             # PPI::Statement
138             # PPI::Token::Word 'PAR::Dist'
139             # PPI::Token::Operator '->'
140             # PPI::Token::Word 'VERSION'
141             # PPI::Structure::List ( ... )
142             # PPI::Statement::Expression
143             # PPI::Token::Number::Float '0.17'
144              
145             try {
146 0     0     my @chunks2 = @{$self->ppi_document->find('PPI::Statement')};
  0            
147 0           foreach my $chunk (@chunks2) {
148 0 0         if (
149             $chunk->find(
150             sub {
151 0 0         $_[1]->isa('PPI::Token::Word')
152             and $_[1]->content =~ m{\A(?:eval|try)\z};
153             }
154             )
155             )
156             {
157 0           for (0 .. $#{$chunk->{children}}) {
  0            
158              
159 0           my $module_name;
160             my $version_string;
161              
162 0 0         if ($chunk->{children}[$_]->isa('PPI::Structure::Block')) {
163              
164             my $ppi_sb = $chunk->{children}[$_]
165 0 0         if $chunk->{children}[$_]->isa('PPI::Structure::Block');
166              
167 0           $self->_eval_info($ppi_sb, \$module_name, \$version_string);
168 0 0         print "Option2 $module_name - $version_string\n" if $self->debug;
169             }
170 0 0         if (version::is_lax($version_string)) {
171              
172 0           push @modules, $module_name;
173 0 0         $version_string
174             = version::is_lax($version_string) ? $version_string : 0;
175 0           push @version_strings, $version_string;
176 0           $self->{found_version}{$module_name} = $version_string;
177             }
178             }
179             }
180             }
181 0           };
182              
183              
184             #PPI::Document
185             # PPI::Statement
186             # PPI::Token::Word 'eval'
187             # PPI::Token::Whitespace ' '
188             # PPI::Token::Quote::Double '"require Test::Kwalitee::Extra $mod_ver"'
189             # PPI::Token::Structure ';'
190             #
191              
192             try {
193 0     0     my @chunks1 = @{$self->ppi_document->find('PPI::Statement')};
  0            
194 0           foreach my $chunk (@chunks1) {
195 0 0         if (
196             $chunk->find(
197             sub {
198 0 0         $_[1]->isa('PPI::Token::Word')
199             and $_[1]->content =~ m{\A(?:eval|try)\z};
200             }
201             )
202             )
203             {
204 0           for (0 .. $#{$chunk->{children}}) {
  0            
205              
206             # ignore sub blocks - false positive
207 0 0         last if $chunk->{children}[$_]->content eq 'sub';
208              
209 0 0 0       if ( $chunk->{children}[$_]->isa('PPI::Token::Quote::Double')
210             || $chunk->{children}[$_]->isa('PPI::Token::Quote::Single'))
211             {
212 0           my $eval_line = $chunk->{children}[$_]->content;
213              
214 0           $eval_line =~ s/(?:'|"|{|})//g;
215 0           my @eval_includes = split /;/, $eval_line;
216              
217 0           foreach my $eval_include (@eval_includes) {
218              
219 0           $self->_mod_ver(\@modules, \@version_strings, $eval_include);
220             }
221             }
222              
223 0 0         if ($chunk->{children}[$_]->isa('PPI::Structure::Block')) {
224 0           my @children = $chunk->{children}[$_]->children;
225              
226 0           foreach my $child_element (@children) {
227 0 0         if ($child_element->isa('PPI::Statement::Include')) {
228              
229 0           my $eval_line = $child_element->content;
230 0           my @eval_includes = split /;/, $eval_line;
231 0           foreach my $eval_include (@eval_includes) {
232 0           $self->_mod_ver(\@modules, \@version_strings,
233             $eval_include);
234             }
235             }
236             }
237             }
238             }
239             }
240             }
241 0           };
242              
243 0 0         p @modules if $self->debug;
244 0 0         p @version_strings if $self->debug;
245              
246 0 0         if (scalar @modules > 0) {
247 0           for (0 .. $#modules) {
248 0 0         print "Info: Eval -> Sending $modules[$_] - $version_strings[$_]\n"
249             if ($self->verbose == TWO);
250              
251             try {
252 0     0     $self->_process_found_modules(
253             $phase_relationship, $modules[$_], $version_strings[$_],
254             __PACKAGE__, $phase_relationship,
255             );
256 0           };
257             }
258             }
259 0           return;
260             }
261              
262              
263             #######
264             # composed Method
265             #######
266             sub _mod_ver {
267 0     0     my ($self, $modules, $version_strings, $eval_include) = @_;
268              
269 0 0         if ($eval_include =~ /^\s*(?:use|require|no)/) {
270              
271 0           $eval_include =~ s/^\s*(?:use|require|no)\s*//;
272              
273 0           my $module_name = $eval_include;
274              
275 0           $module_name =~ s/(?:\s[\s|\w|\n|.|;]+)$//;
276 0           $module_name =~ s/\s+(?:[\$|\w|\n]+)$//;
277 0           $module_name =~ s/\s+$//;
278              
279 0           $module_name =~ m/\A([\w|:]+)\b/;
280 0           $module_name = $1;
281              
282             # exit if already found by this extra scanner
283 0 0         return if $self->{found_version}{$module_name};
284              
285             # check for first char upper in module name
286 0 0         push @{$modules}, $module_name if $module_name =~ m{\A(?:[a-zA-Z])};
  0            
287              
288              
289 0           my $version_string = $eval_include;
290 0           $version_string =~ s/$module_name\s*//;
291 0           $version_string =~ s/\s*$//;
292 0           $version_string =~ s/[a-zA-Z]|\s|\$|s|:|;//g;
293              
294 0 0         $version_string = version::is_lax($version_string) ? $version_string : 0;
295 0           push @{$version_strings}, $version_string;
  0            
296 0           $self->{found_version}{$module_name} = $version_string;
297 0 0         print "Option1 $module_name - $version_string\n" if $self->debug;
298             }
299              
300 0           return;
301             }
302              
303              
304             #######
305             # composed Method
306             #######
307             sub _eval_info {
308 0     0     my ($self, $ppi_sb, $mn_ref, $vs_ref) = @_;
309              
310 0           for (0 .. $#{$ppi_sb->{children}}) {
  0            
311              
312             # find module name
313 0 0         if ($ppi_sb->{children}[$_]->isa('PPI::Statement::Include')) {
314             my $ppi_si = $ppi_sb->{children}[$_]
315 0 0         if $ppi_sb->{children}[$_]->isa('PPI::Statement::Include');
316 0 0 0       if ( $ppi_si->{children}[0]->isa('PPI::Token::Word')
317             && $ppi_si->{children}[0]->content eq 'require')
318             {
319 0           ${$mn_ref} = $ppi_si->{children}[2]->content
320 0 0         if $ppi_si->{children}[2]->isa('PPI::Token::Word');
321             }
322             }
323              
324             # find version string if we previously found a name
325 0 0         if ($ppi_sb->{children}[$_]->isa('PPI::Statement')) {
326             my $ppi_s = $ppi_sb->{children}[$_]
327 0 0         if $ppi_sb->{children}[$_]->isa('PPI::Statement');
328 0 0 0       if (
      0        
      0        
329             (
330             $ppi_s->{children}[0]->isa('PPI::Token::Word')
331 0           and $ppi_s->{children}[0]->content eq ${$mn_ref}
332             )
333             && ( $ppi_s->{children}[2]->isa('PPI::Token::Word')
334             and $ppi_s->{children}[2]->content eq 'VERSION')
335             )
336             {
337             my $ppi_sl = $ppi_s->{children}[3]
338 0 0         if $ppi_s->{children}[3]->isa('PPI::Structure::List');
339 0           ${$vs_ref} = $ppi_sl->{children}[0]->{children}[0]->content;
  0            
340             }
341             }
342             }
343              
344 0           return;
345             }
346              
347 2     2   4110 no Moo::Role;
  2         3  
  2         12  
348              
349             1;
350              
351             __END__
352              
353             =pod
354              
355             =encoding UTF-8
356              
357             =head1 NAME
358              
359             App::Midgen::Roles::Eval - used by L<App::Midgen>
360              
361             =head1 VERSION
362              
363             This document describes App::Midgen::Roles version: 0.33_05
364              
365             =head1 METHODS
366              
367             =over 4
368              
369             =item * xtests_eval
370              
371             Checking for the following, extracting module name and version string.
372              
373             eval {use Test::Kwalitee::Extra 0.000007};
374             eval {use Moo 1.002; 1;};
375             eval { no Moose; 1; };
376             eval { require Moose };
377             my $HAVE_MOOSE = eval { require Moose; 1; };
378              
379             try { no Moose; 1; };
380             try { require Moose };
381             my $HAVE_MOOSE = try { require Moose; 1; };
382              
383             eval {require PAR::Dist; PAR::Dist->VERSION(0.17)}
384              
385             =back
386              
387             =head1 SEE ALSO
388              
389             L<App::Midgen>,
390              
391             =head1 AUTHOR
392              
393             See L<App::Midgen>
394              
395             =head2 CONTRIBUTORS
396              
397             See L<App::Midgen>
398              
399             =head1 COPYRIGHT
400              
401             See L<App::Midgen>
402              
403             =head1 LICENSE
404              
405             This library is free software; you can redistribute it and/or modify
406             it under the same terms as Perl itself.
407              
408