File Coverage

blib/lib/IO/All/Dir.pm
Criterion Covered Total %
statement 110 139 79.1
branch 37 48 77.0
condition 17 25 68.0
subroutine 28 37 75.6
pod 22 24 91.6
total 214 273 78.3


line stmt bran cond sub pod time code
1 17     17   1355 use strict; use warnings;
  17     17   28  
  17         628  
  17         70  
  17         28  
  17         651  
2             package IO::All::Dir;
3              
4 17     17   71 use Scalar::Util 'blessed';
  17         83  
  17         1015  
5 17     17   83 use File::Glob 'bsd_glob';
  17         34  
  17         1373  
6 17     17   377 use IO::All::Filesys -base;
  17         22  
  17         141  
7 17     17   146 use IO::All -base;
  17         34  
  17         100  
8 17     17   8360 use IO::Dir;
  17         148361  
  17         23713  
9              
10             #===============================================================================
11             const type => 'dir';
12             option 'sort' => 1;
13             chain filter => undef;
14             option 'deep';
15             field 'chdir_from';
16              
17             #===============================================================================
18             sub dir {
19 232     232 1 226 my $self = shift;
20 232   66     1213 my $had_prev = blessed($self) && $self->pathname;
21              
22 232 100       637 bless $self, __PACKAGE__ unless $had_prev;
23 232 100 100     1774 if (@_ && @_ > 1 || @_ && $had_prev) {
    100 100        
      66        
24 12 100       44 $self->name(
25             $self->_spec_class->catdir(
26             ($self->pathname ? ($self->pathname) : () ),
27             @_,
28             )
29             )
30             } elsif (@_) {
31 219         473 $self->name($_[0])
32             }
33 232         525 return $self->_init;
34             }
35              
36             sub dir_handle {
37 0     0 0 0 my $self = shift;
38 0         0 bless $self, __PACKAGE__;
39 0 0       0 $self->_handle(shift) if @_;
40 0         0 return $self->_init;
41             }
42              
43             #===============================================================================
44             sub _assert_open {
45 935     935   709 my $self = shift;
46 935 100       1538 return if $self->is_open;
47 137         290 $self->open;
48             }
49              
50             sub open {
51 137     137 1 154 my $self = shift;
52 137         256 $self->is_open(1);
53 137 50 33     260 $self->_assert_dirpath($self->pathname)
54             if $self->pathname and $self->_assert;
55 137         611 my $handle = IO::Dir->new;
56 137         2451 $self->io_handle($handle);
57 137 100       295 $handle->open($self->pathname)
58             or $self->throw($self->open_msg);
59 136         4872 return $self;
60             }
61              
62             sub open_msg {
63 1     1 0 40 my $self = shift;
64 1 50       3 my $name = defined $self->pathname
65             ? " '" . $self->pathname . "'"
66             : '';
67 1         15 return qq{Can't open directory$name:\n$!};
68             }
69              
70 0     0 1 0 sub exists { -d shift->pathname }
71              
72             #===============================================================================
73             sub All {
74 1     1 1 2 my $self = shift;
75 1         4 $self->all(0);
76             }
77              
78             sub all {
79 133     133 1 558 my $self = shift;
80 133 100       260 my $depth = @_ ? shift(@_) : $self->_deep ? 0 : 1;
    100          
81 133         173 my $first = not @_;
82 133         101 my @all;
83 133         222 while (my $io = $self->next) {
84 311         342 push @all, $io;
85 311 100 100     1082 push(@all, $io->all($depth - 1, 1))
86             if $depth != 1 and $io->is_dir;
87             }
88 133 100       354 @all = grep {&{$self->filter}} @all
  20         16  
  20         32  
89             if $self->filter;
90 133 100 66     664 return @all unless $first and $self->_sort;
91 38         168 return sort {$a->pathname cmp $b->pathname} @all;
  631         1062  
92             }
93              
94             sub All_Dirs {
95 3     3 1 4 my $self = shift;
96 3         8 $self->all_dirs(0);
97             }
98              
99             sub all_dirs {
100 11     11 1 14 my $self = shift;
101 11         24 grep {$_->is_dir} $self->all(@_);
  82         128  
102             }
103              
104             sub All_Files {
105 3     3 1 5 my $self = shift;
106 3         8 $self->all_files(0);
107             }
108              
109             sub all_files {
110 13     13 1 19 my $self = shift;
111 13         34 grep {$_->is_file} $self->all(@_);
  112         201  
112             }
113              
114             sub All_Links {
115 0     0 1 0 my $self = shift;
116 0         0 $self->all_links(0);
117             }
118              
119             sub all_links {
120 0     0 1 0 my $self = shift;
121 0         0 grep {$_->is_link} $self->all(@_);
  0         0  
122             }
123              
124             sub chdir {
125 1     1 1 5 my $self = shift;
126 1         8 require Cwd;
127 1         3074 $self->chdir_from(Cwd::cwd());
128 1         12 CORE::chdir($self->pathname);
129 1         10 return $self;
130             }
131              
132             sub empty {
133 1     1 1 2 my $self = shift;
134 1         1 my $dh;
135 1 50       8 opendir($dh, $self->pathname) or die;
136 1         26 while (my $dir = readdir($dh)) {
137 2 50       12 return 0 unless $dir =~ /^\.{1,2}$/;
138             }
139 1         12 return 1;
140             }
141              
142             sub mkdir {
143 1     1 1 6 my $self = shift;
144 1 50 0     8 defined($self->perms)
      50        
145             ? (CORE::mkdir($self->pathname, $self->perms) or die "mkdir failed: $!")
146             : (CORE::mkdir($self->pathname) or die "mkdir failed: $!");
147 1         8 return $self;
148             }
149              
150             sub mkpath {
151 0     0 1 0 my $self = shift;
152 0         0 require File::Path;
153 0         0 File::Path::mkpath($self->pathname, @_);
154 0         0 return $self;
155             }
156              
157             sub file {
158 0     0 1 0 my ($self, @rest) = @_;
159              
160 0         0 return $self->_constructor->()->file($self->pathname, @rest)
161             }
162              
163             sub next {
164 468     468 1 451 my $self = shift;
165 468         804 $self->_assert_open;
166 467         818 my $name = $self->readdir;
167 467 100       1118 return unless defined $name;
168 332         751 my $io = $self->_constructor->(File::Spec->catfile($self->pathname, $name));
169 332 100       1070 $io->absolute if $self->is_absolute;
170 332         908 return $io;
171             }
172              
173             sub readdir {
174 467     467 1 431 my $self = shift;
175 467         584 $self->_assert_open;
176 467 50       764 if (wantarray) {
177 0         0 my @return = grep {
178 0         0 not /^\.{1,2}$/
179             } $self->io_handle->read;
180 0         0 $self->close;
181 0         0 return @return;
182             }
183 467         475 my $name = '.';
184 467         2116 while ($name =~ /^\.{1,2}$/) {
185 737         1362 $name = $self->io_handle->read;
186 737 100       6184 unless (defined $name) {
187 135         487 $self->close;
188 135         1987 return;
189             }
190             }
191 332         568 return $name;
192             }
193              
194             sub rmdir {
195 0     0 1 0 my $self = shift;
196 0         0 rmdir $self->pathname;
197             }
198              
199             sub rmtree {
200 0     0 1 0 my $self = shift;
201 0         0 require File::Path;
202 0         0 File::Path::rmtree($self->pathname, @_);
203             }
204              
205             sub glob {
206 1     1 1 3 my ($self, @rest) = @_;
207              
208 1         5 map {;
209 3         23 my $ret = $self->_constructor->($_);
210 3 50       16 $ret->absolute if $self->is_absolute;
211 3         22 $ret
212             } bsd_glob $self->_spec_class->catdir( $self->pathname, @rest );
213             }
214              
215             sub copy {
216 0     0 1 0 my ($self, $new) = @_;
217              
218 0         0 require File::Copy::Recursive;
219              
220 0 0       0 File::Copy::Recursive::dircopy($self->name, $new)
221             or die "failed to copy $self to $new: $!";
222 0         0 $self->_constructor->($new)
223             }
224              
225             sub DESTROY {
226 232     232   6652 my $self = shift;
227 232 100       429 CORE::chdir($self->chdir_from)
228             if $self->chdir_from;
229             # $self->SUPER::DESTROY(@_);
230             }
231              
232             #===============================================================================
233             sub _overload_table {
234             (
235 4     4   18 '${} dir' => '_overload_as_scalar',
236             '@{} dir' => '_overload_as_array',
237             '%{} dir' => '_overload_as_hash',
238             )
239             }
240              
241             sub _overload_as_scalar {
242 1     1   4 \ $_[1];
243             }
244              
245             sub _overload_as_array {
246 1     1   2 [ $_[1]->all ];
247             }
248              
249             sub _overload_as_hash {
250             +{
251 10         19 map {
252 2     2   5 (my $name = $_->pathname) =~ s/.*[\/\\]//;
253 10         32 ($name, $_);
254             } $_[1]->all
255             };
256             }
257              
258             1;