File Coverage

blib/lib/Path/Class/File.pm
Criterion Covered Total %
statement 105 121 86.7
branch 39 68 57.3
condition 6 10 60.0
subroutine 24 29 82.7
pod 20 21 95.2
total 194 249 77.9


line stmt bran cond sub pod time code
1 7     7   18089 use strict;
  7         7  
  7         275  
2              
3             package Path::Class::File;
4             {
5             $Path::Class::File::VERSION = '0.37';
6             }
7              
8 7     7   2787 use Path::Class::Dir;
  7         12  
  7         163  
9 7     7   29 use parent qw(Path::Class::Entity);
  7         7  
  7         27  
10 7     7   301 use Carp;
  7         8  
  7         282  
11              
12 7     7   22 use IO::File ();
  7         7  
  7         1475  
13              
14             sub new {
15 158     158 1 904 my $self = shift->SUPER::new;
16 158         161 my $file = pop();
17 158         175 my @dirs = @_;
18              
19 158         273 my ($volume, $dirs, $base) = $self->_spec->splitpath($file);
20              
21 158 100       331 if (length $dirs) {
22 24         45 push @dirs, $self->_spec->catpath($volume, $dirs, '');
23             }
24              
25 158 100       356 $self->{dir} = @dirs ? $self->dir_class->new(@dirs) : undef;
26 158         192 $self->{file} = $base;
27              
28 158         325 return $self;
29             }
30              
31 153     153 1 408 sub dir_class { "Path::Class::Dir" }
32              
33             sub as_foreign {
34 18     18 1 1135 my ($self, $type) = @_;
35 18         36 local $Path::Class::Foreign = $self->_spec_class($type);
36 18         70 my $foreign = ref($self)->SUPER::new;
37 18 50       89 $foreign->{dir} = $self->{dir}->as_foreign($type) if defined $self->{dir};
38 18         30 $foreign->{file} = $self->{file};
39 18         49 return $foreign;
40             }
41              
42             sub stringify {
43 302     302 1 5203 my $self = shift;
44 302 100       646 return $self->{file} unless defined $self->{dir};
45 298         511 return $self->_spec->catfile($self->{dir}->stringify, $self->{file});
46             }
47              
48             sub dir {
49 21     21 1 987 my $self = shift;
50 21 100       77 return $self->{dir} if defined $self->{dir};
51 1         4 return $self->dir_class->new($self->_spec->curdir);
52             }
53 7     7   5947 BEGIN { *parent = \&dir; }
54              
55             sub volume {
56 0     0 1 0 my $self = shift;
57 0 0       0 return '' unless defined $self->{dir};
58 0         0 return $self->{dir}->volume;
59             }
60              
61             sub components {
62 8     8 1 27 my $self = shift;
63 8 50       12 croak "Arguments are not currently supported by File->components()" if @_;
64 8         9 return ($self->dir->components, $self->basename);
65             }
66              
67 18     18 1 69 sub basename { shift->{file} }
68 42     42 1 1013 sub open { IO::File->new(@_) }
69              
70 0 0   0 1 0 sub openr { $_[0]->open('r') or croak "Can't read $_[0]: $!" }
71 19 50   19 1 30 sub openw { $_[0]->open('w') or croak "Can't write to $_[0]: $!" }
72 0 0   0 1 0 sub opena { $_[0]->open('a') or croak "Can't append to $_[0]: $!" }
73              
74             sub touch {
75 19     19 1 23 my $self = shift;
76 19 50       45 if (-e $self) {
77 0         0 utime undef, undef, $self;
78             } else {
79 19         35 $self->openw;
80             }
81             }
82              
83             sub slurp {
84 13     13 1 1974 my ($self, %args) = @_;
85 13   100     45 my $iomode = $args{iomode} || 'r';
86 13 50       25 my $fh = $self->open($iomode) or croak "Can't read $self: $!";
87              
88 13 100       83 if (wantarray) {
89 6         62 my @data = <$fh>;
90 6 100 33     22 chomp @data if $args{chomped} or $args{chomp};
91              
92 6 100       13 if ( my $splitter = $args{split} ) {
93 2         2 @data = map { [ split $splitter, $_ ] } @data;
  4         31  
94             }
95              
96 6         59 return @data;
97             }
98              
99              
100             croak "'split' argument can only be used in list context"
101 7 50       14 if $args{split};
102              
103              
104 7 50 33     22 if ($args{chomped} or $args{chomp}) {
105 0         0 chomp( my @data = <$fh> );
106 0         0 return join '', @data;
107             }
108              
109              
110 7         21 local $/;
111 7         146 return <$fh>;
112             }
113              
114             sub spew {
115 6     6 1 20 my $self = shift;
116 6         15 my %args = splice( @_, 0, @_-1 );
117              
118 6   100     19 my $iomode = $args{iomode} || 'w';
119 6 50       11 my $fh = $self->open( $iomode ) or croak "Can't write to $self: $!";
120              
121 6 100       47 if (ref($_[0]) eq 'ARRAY') {
122             # Use old-school for loop to avoid copying.
123 1         3 for (my $i = 0; $i < @{ $_[0] }; $i++) {
  5         8  
124 4 50       10 print $fh $_[0]->[$i]
125             or croak "Can't write to $self: $!";
126             }
127             }
128             else {
129 5 50       27 print $fh $_[0]
130             or croak "Can't write to $self: $!";
131             }
132              
133 6 50       125 close $fh
134             or croak "Can't write to $self: $!";
135              
136 6         27 return;
137             }
138              
139             sub spew_lines {
140 2     2 1 11 my $self = shift;
141 2         7 my %args = splice( @_, 0, @_-1 );
142              
143 2         3 my $content = $_[0];
144              
145             # If content is an array ref, appends $/ to each element of the array.
146             # Otherwise, if it is a simple scalar, just appends $/ to that scalar.
147              
148             $content
149             = ref( $content ) eq 'ARRAY'
150 2 100       6 ? [ map { $_, $/ } @$content ]
  2         5  
151             : "$content$/";
152              
153 2         5 return $self->spew( %args, $content );
154             }
155              
156             sub remove {
157 7     7 1 1104 my $file = shift->stringify;
158 7 50       92 return unlink $file unless -e $file; # Sets $! correctly
159 7         356 1 while unlink $file;
160 7         27 return not -e $file;
161             }
162              
163             sub copy_to {
164 2     2 1 7 my ($self, $dest) = @_;
165 2 100       4 if ( eval{ $dest->isa("Path::Class::File")} ) {
  2 50       21  
    0          
166 1         2 $dest = $dest->stringify;
167 1 50       28 croak "Can't copy to file $dest: it is a directory" if -d $dest;
168 1         7 } elsif ( eval{ $dest->isa("Path::Class::Dir") } ) {
169 1         3 $dest = $dest->stringify;
170 1 50       13 croak "Can't copy to directory $dest: it is a file" if -f $dest;
171 1 50       8 croak "Can't copy to directory $dest: no such directory" unless -d $dest;
172             } elsif ( ref $dest ) {
173 0         0 croak "Don't know how to copy files to objects of type '".ref($self)."'";
174             }
175              
176 2         521 require Perl::OSType;
177 2 50       390 if ( !Perl::OSType::is_os_type('Unix') ) {
178              
179 0         0 require File::Copy;
180 0 0       0 return unless File::Copy::cp($self->stringify, "${dest}");
181              
182             } else {
183              
184 2 50       25 return unless (system('cp', $self->stringify, "${dest}") == 0);
185              
186             }
187              
188 2         46 return $self->new($dest);
189             }
190              
191             sub move_to {
192 1     1 1 2 my ($self, $dest) = @_;
193 1         523 require File::Copy;
194 1 50       1849 if (File::Copy::move($self->stringify, "${dest}")) {
195              
196 1         66 my $new = $self->new($dest);
197              
198 1         6 $self->{$_} = $new->{$_} foreach (qw/ dir file /);
199              
200 1         3 return $self;
201              
202             } else {
203              
204 0         0 return;
205              
206             }
207             }
208              
209             sub traverse {
210 12     12 1 11 my $self = shift;
211 12         7 my ($callback, @args) = @_;
212 12     12   24 return $self->$callback(sub { () }, @args);
  12         38  
213             }
214              
215             sub traverse_if {
216 0     0 0   my $self = shift;
217 0           my ($callback, $condition, @args) = @_;
218 0     0     return $self->$callback(sub { () }, @args);
  0            
219             }
220              
221             1;
222             __END__