1package Toader::Render::Page::Cleanup;
2
3use warnings;
4use strict;
5use base 'Error::Helper';
6use Toader::pathHelper;
7
8=head1 NAME
9
10Toader::Render::Page::Cleanup - This is used for cleaning up the output directory prior to rendering.
11
12=head1 VERSION
13
14Version 0.1.0
15
16=cut
17
18our $VERSION = '0.1.0';
19
20
21=head1 SYNOPSIS
22
23=head1 METHODS
24
25=head2 new
26
27This initiates the object.
28
29One argument is required and it is a L<Toader> object.
30
31	my $foo=Toader::Render::Page::Cleanup->new($toader);
32    if($foo->error){
33        warn('error: '.$foo->error.":".$foo->errorString);
34    }
35
36=cut
37
38sub new{
39	my $toader=$_[1];
40
41	my $self={
42			  error=>undef,
43			  errorString=>'',
44			  perror=>undef,
45			  errorExtra=>{
46				  flags=>{
47					  1=>'noToaderObj',
48					  2=>'notAtoaderObj',
49					  3=>'toaderPerror',
50					  4=>'notApageObj',
51					  5=>'noObj',
52					  6=>'noOutputdirSet',
53					  7=>'outputDirDoesNotExist',
54					  8=>'objPerror',
55					  9=>'noDirSet',
56					  10=>'pathhelperErrored',
57					  11=>'cleanupFailed',
58				  },
59			  },
60			  };
61	bless $self;
62
63	#make sure something passed to this method
64	if ( ! defined( $toader ) ){
65		$self->{error}=1;
66		$self->{errorString}='No Toader object passed';
67		$self->{perror}=1;
68		$self->warn;
69		return $self;
70	}
71
72	#makes sure the object passed is a Toader object
73	if ( ref( $toader ) ne 'Toader' ){
74		$self->{error}=2;
75		$self->{errorString}='The passed object is not a Toader object, but a "'
76			.ref( $toader ).'"';
77		$self->{perror}=1;
78		$self->warn;
79		return $self;
80	}
81
82	#makes sure the toader object is not in a permanent error state
83	$toader->errorblank;
84	if ( $toader->error ){
85		$self->{perror}=1;
86		$self->{error}=3;
87		$self->{errorString}='The Toader object passed has a permanent error set. error="'.
88			$toader->error.'" errorString="'.$toader->errorString.'"';
89		$self->warn;
90		return $self;
91	}
92
93	$self->{toader}=$toader;
94
95	#makes sure a output directory is set
96	my $outputdir=$self->{toader}->getOutputDir;
97	if( ! defined( $outputdir ) ){
98		$self->{error}=6;
99		$self->{errorString}='The Toader object has not had a output directory set';
100		$self->warn;
101		return undef;
102	}
103	$self->{outputdir}=$outputdir;
104
105	#make sure the output directory exists
106	if( ! -d $outputdir ){
107		$self->{error}=7;
108		$self->{errorString}='The output directory does not exist or does not appear to be a directory';
109		$self->warn;
110		return undef;
111	}
112
113	#gets the pathhelper for later usage
114	$self->{pathhelper}=$self->{toader}->getPathHelper;
115
116	return $self;
117}
118
119=head2 cleanup
120
121This cleans up the output directory for a specified object.
122
123One argument is taken and that is the object to be cleaned from
124the output directory.
125
126    $foo->cleanup( $obj );
127    if($foo->error){
128        warn('error: '.$foo->error.":".$foo->errorString);
129    }
130
131=cut
132
133sub cleanup{
134	my $self=$_[0];
135	my $obj=$_[1];
136
137	if (!$self->errorblank){
138		return undef;
139	}
140
141	#make sure a object was passed
142	if ( ! defined( $obj ) ){
143		$self->{error}=5;
144		$self->{errorString}='No object passed';
145		$self->warn;
146		return $self;
147	}
148
149	#make sure it is a supported type
150	if ( ref( $obj ) ne 'Toader::Page' ){
151		$self->{error}=4;
152		$self->{errorString}='"'.ref( $obj ).'" is not a supported object type';
153		$self->warn;
154		return $self;
155	}
156
157	#make sure a permanent error is not set
158	$obj->errorblank;
159	if( $obj->error ){
160		$self->{error}=8;
161		$self->{errorString}='The object error has a permanent error set. error="'
162			.$obj->error.'" errorString="'.$obj->errorString.'"';
163		$self->warn;
164		return undef;
165	}
166
167	#gets the directory
168	my $dir=$obj->dirGet;
169	if ( ! defined( $dir ) ){
170		$self->{error}=9;
171		$self->{errorString}='The object has not had a directory set for it';
172		$self->warn;
173		return undef;
174	}
175
176	#puts together the base directory
177	$dir=$self->{outputdir}.'/'.$self->{pathhelper}->relative2root($dir).'/';
178	if( $self->{pathhelper}->error ){
179		$self->{error}=10;
180		$self->{errorString}='Toader::pathHelper errored. error="'.
181			$self->{pathhelper}->error.'" errorString="'.
182			$self->{pathhelper}->errorString.'"';
183		$self->warn;
184		return undef;
185	}
186	$dir=$dir.'.pages/'.$obj->nameGet.'/';
187
188	#if the directory does not exist, there is nothing to clean up
189	if ( ! -e $dir ){
190		return 1;
191	}
192
193	#a list of files that could not be removed
194	my @failed;
195
196	#tries to remove the index file
197	my $index=$dir.'index.html';
198	my $indexNotAfile=0;
199	if ( -f $index ){
200		if( ! unlink( $index ) ){
201			push( @failed, $index );
202		}
203	}else{
204		if ( -e $index ){
205			$indexNotAfile=1;
206			push( @failed, $index );
207		}
208	}
209
210	#tries to remove the attached files
211	my $filesdir=$dir.'.files/';
212	my @files;
213	my $dh;
214	my $openFilesdirFailed=0;
215	if (! opendir( $dh, $filesdir ) ){
216		if ( -e $filesdir ){
217			$openFilesdirFailed=0;
218		}
219	}else{
220		@files=readdir( $dh );
221		closedir( $dh );
222	}
223
224	#removes each file
225	my $int=0;
226	my $foundAnonFile=0;
227	my @nonfiles;
228	while ( defined( $files[$int] ) ){
229		my $path=$filesdir.$files[$int];
230
231		#determines if it should be skipped
232		my $skip=0;
233
234		#skips .. or .
235		if (
236			( $files[$int] eq '.' ) ||
237			( $files[$int] eq '..' )
238			){
239			$skip=1;
240		}
241
242		#skip non-files
243		if (
244			( ! -f $path ) &&
245			( ! $skip )
246			){
247			$skip=1;
248			push( @nonfiles, $path );
249		}
250
251		if ( ! $skip ){
252			if( ! unlink( $path) ){
253				push( @failed, $path );
254			}
255		}
256
257		$int++;
258	}
259
260	#removes the files directory
261	my $fileDirRMfailed=0;
262	if(
263		(
264		 ( ! defined( $nonfiles[0] ) ) ||
265		 ( ! defined( $failed[0] ) )
266		) &&
267		( -e $filesdir )
268		){
269		if( ! rmdir $filesdir ){
270			$fileDirRMfailed=1;
271		};
272	}
273
274	#checks to see if the obj directory can be removed and if so remove it
275	my $objDirRMfailed=0;
276	if ( ! -e $filesdir ){
277			if (! opendir( $dh, $dir ) ){
278				$openFilesdirFailed=0;
279			}else{
280				@files=readdir( $dh );
281				closedir( $dh );
282			}
283
284			if (opendir( $dh, $filesdir ) ){
285				@files=readdir( $dh );
286				closedir( $dh );
287			}
288
289			$int=0;
290			my $rmObjDir=1;
291			while ( defined( $files[$int] ) ){
292				if (
293					( $files[$int] ne '.' ) ||
294					( $files[$int] ne '..' )
295					){
296					$rmObjDir=0;
297				}
298
299				$int++;
300			}
301
302			if ( $rmObjDir ){
303				if ( ! rmdir( $dir ) ){
304					$objDirRMfailed=1;
305				}
306			}
307
308	}
309
310	#handles it if it errored
311	if(
312		defined( $nonfiles[0] )||
313		$openFilesdirFailed ||
314		$indexNotAfile ||
315		$fileDirRMfailed ||
316		$objDirRMfailed ||
317		defined( $failed[0] )
318		){
319
320		my $error='';
321
322		if ( $indexNotAfile  ){
323			$error='The index file, "'.$index.'", could not be removed. ';
324		}
325
326		if ( $openFilesdirFailed ){
327			$error=$error.'Could not open the files directory for reading ';
328		}
329
330		if ( $fileDirRMfailed ){
331			$error=$error.'Failed to remove the files directory, "'.$filesdir.'". ';
332		}
333
334		if ( $objDirRMfailed ){
335			$error=$error.'Failed to remove the object directory, "'.$dir.'".';
336		}
337
338		my $int=0;
339
340		if ( defined( $nonfiles[0] ) ){
341			$error=$error.'Some none files were found... ';
342			while ( defined( $nonfiles[$int] ) ){
343				$error=$error.'"'.$nonfiles[$int].'" ';
344
345				$int++;
346			}
347		}
348
349		if ( defined( $failed[0] ) ){
350			$error=$error.'Some files could not be removed... ';
351			$int=0;
352			while ( defined( $failed[$int] ) ){
353				$error=$error.'"'.$failed[$int].'" ';
354
355				$int++;
356			}
357		}
358
359		$self->{error}=11;
360		$self->{errorString}=$error;
361		$self->warn;
362		return undef;
363	}
364
365	return 1;
366}
367
368=head1 ERROR CODES
369
370=head2 1, noToaderObj
371
372No L<Toader> object passed.
373
374=head2 2, notAtoaderObj
375
376The passed object is not a L<Toader> object.
377
378=head2 3, toaderPerror
379
380The L<Toader> object passed has a permanent error set.
381
382=head2 4, notApageObj
383
384The passed object is not a L<Toader::Page> object.
385
386=head2 5, noObj
387
388No object passed.
389
390=head2 6, noOutputDirSet
391
392The L<Toader> object has not had a output directory set.
393
394=head2 7, outputDirDoesNotExist
395
396The output directory does not appear to exist or is not a directory.
397
398=head2 8, objPerror
399
400The object has a permanent error set.
401
402=head2 9, noDirSet
403
404The object has not had a directory set for it.
405
406=head2 10, pathhelperErrored
407
408L<Toader::pathHelper> errored.
409
410=head2 11, cleanupFailed
411
412Cleaned errored. See error message.
413
414=head1 AUTHOR
415
416Zane C. Bowers-Hadley, C<< <vvelox at vvelox.net> >>
417
418=head1 BUGS
419
420Please report any bugs or feature requests to C<bug-toader at rt.cpan.org>, or through
421the web interface at L<http://rt.cpan.org/NoAuth/ReportBug.html?Queue=Toader>.  I will be notified, and then you'll
422automatically be notified of progress on your bug as I make changes.
423
424
425
426
427=head1 SUPPORT
428
429You can find documentation for this module with the perldoc command.
430
431    perldoc Toader::Render::Page::Cleanup
432
433You can also look for information at:
434
435=over 4
436
437=item * RT: CPAN's request tracker
438
439L<http://rt.cpan.org/NoAuth/Bugs.html?Dist=Toader>
440
441=item * AnnoCPAN: Annotated CPAN documentation
442
443L<http://annocpan.org/dist/Toader>
444
445=item * CPAN Ratings
446
447L<http://cpanratings.perl.org/d/Toader>
448
449=item * Search CPAN
450
451L<http://search.cpan.org/dist/Toader/>
452
453=back
454
455
456=head1 ACKNOWLEDGEMENTS
457
458
459=head1 LICENSE AND COPYRIGHT
460
461Copyright 2013. Zane C. Bowers-Hadley.
462
463This program is free software; you can redistribute it and/or modify it
464under the terms of either: the GNU General Public License as published
465by the Free Software Foundation; or the Artistic License.
466
467See http://dev.perl.org/licenses/ for more information.
468
469=cut
470
4711; # End of Toader::Render::Page::Cleanup
472