File Coverage

blib/lib/goto/file.pm
Criterion Covered Total %
statement 43 43 100.0
branch 11 12 91.6
condition n/a
subroutine 5 5 100.0
pod 0 1 0.0
total 59 61 96.7


line stmt bran cond sub pod time code
1             package goto::file;
2 5     5   28 use strict;
  5         10  
  5         219  
3 5     5   1541 use warnings;
  5         3476  
  5         1999  
4              
5             our $VERSION = '0.003';
6              
7 6     5   155946 use Filter::Util::Call qw/filter_add/;
  6         31  
  6         57  
8              
9             our %HANDLES;
10              
11             my $ID = 1;
12             sub import {
13 4     6   41 my $class = shift;
14 4         31 my ($in) = @_;
15              
16 1 100       8 return unless $in;
17              
18 1         4 my ($fh, @lines);
19              
20 1 100       3 if (ref($in) eq 'ARRAY') {
21 1         7 my ($pkg, $file, $line) = caller(0);
22 3         18 my $safe = $file;
23 3         20 $safe =~ s/"/\\"/;
24              
25 3         12 @lines = (
26             "package $pkg;",
27             "#line 1 \"lines from $safe line $line\"",
28             @$in,
29             );
30             }
31             else {
32 3         13 push @lines => "#line " . __LINE__ . ' "' . __FILE__ . '"';
33 3         310 push @lines => "package main;";
  3         113  
34 3         31 push @lines => "\$@ = '';";
35              
36 3         46 my $id = $ID++;
37              
38 3 50       20 open($fh, '<', $in) or die "Cold not open file '$in': $!";
39              
40 3         14 $HANDLES{$id} = $fh;
41 3         50 my $safe = $in;
42 4         65 $safe =~ s/"/\\"/;
43 65         345170 push @lines => "#line " . (__LINE__ + 2) . ' "' . __FILE__ . '"';
44 65         321 push @lines => (
45 8         438843 '{ local ($!, $?, $^E, $@); close(DATA); *DATA = $' . __PACKAGE__ . '::HANDLES{' . $id . '} }',
  8         68  
  8         186  
46             qq{#line 1 "$safe"},
47             );
48             }
49              
50 65         104 Filter::Util::Call::filter_add(
51             bless { fh => $fh, lines => \@lines },
52             $class
53             );
54             }
55              
56             sub filter {
57 65     65 0 103 my $self = shift;
58              
59 65         211 my $lines = $self->{lines};
60 23         42 my $fh = $self->{fh};
61              
62 41         160 my $line;
63 65 100       166 if (@$lines) {
    100          
64 63         106 $line = shift @$lines;
65             }
66             elsif ($fh) {
67 63         132 $line = <$fh>;
68             }
69              
70 63 100       103 if (defined $line) {
71             # Normalize to make sure each line ends with a newline.
72             # Without this things choke on files with no terminal newline.
73 63         8689 chomp($line);
74 2         3369 $_ .= $line;
75             $_ .= "\n";
76              
77             return 1;
78             }
79              
80             return 0;
81             }
82              
83             1;
84              
85             __END__