http://www.perlmonks.org?node_id=1000350

rrrrr has asked for the wisdom of the Perl Monks concerning the following question:

Hi all,
#!/usr/bin/perl -w use warnings; use strict; use File::Find; use File::Path; my $dir='D:\\TestDelete\Test'; print("$dir"); find \&unwanted,$dir; sub unwanted { if(-d $dir) { if ( ( -M $_ ) >2 &&(-M $_)<4) { print ("file exist"); rmtree($_) or die "could not rmdir '$File::Find::name' $!"; print("deleted"); } } }

The above code is working fine and deleting but before deleting am getting the below error msg Can't remove directory . (Permission denied) at D:\maestro\Testp2.pl line 15. I am ruunning the code in window server which has sep username and password to login. Kindly help me.

Update

Hi all,

My code is working fine as per my requirement .but the thing is am getting the error msg as mentioned above.

Replies are listed 'Best First'.
Re: Can't remove directory-Permission denied
by kennethk (Abbot) on Oct 22, 2012 at 14:33 UTC
    I'm pretty sure you never want to delete your working directory; and I'm pretty sure that's what the warning says you are trying to do. I would suggest including a line in your unwanted routine that says something like return unless /[^.]/;.

    #11929 First ask yourself `How would I do this without a computer?' Then have the computer do it the same way.

      return unless /[^.]/;

      I'm not unsure that it isn't impossible to avoid not including more negations without having to avoid a lack of not trying.

      return if /^\.{1,2}\z/;

      The 'return' still represents one implied negation ("don't do the following"). Each additional negation adds the chance for mentally dropping the negation and introducing a bug or wasting too much time getting very confused.

      It also doesn't skip directories named "...". :) And, of course, that code is assuming a Unix or Windows file system.

      - tye        

        I'm not unsure that it isn't impossible to avoid not including more negations without having to avoid a lack of not trying.

        Clarity itself to a logician, certainly, but — on the offchance that some following along at home might need a little help — let Perl elucidate:

        #! perl use strict; use warnings; my $str1 = "I'm not unsure that it isn't impossible to " . "avoid not including more negations without " . "having to avoid a lack of not trying."; my $str2 = $str1; my %negs = ("not un" => "", "it isn't im" => "it's ", "avoid not including" => "include", "without having to avoid" => "by", "a lack of not" => ""); # Collapse double negatives while (my ($key, $value) = each %negs) { $str2 =~ s/$key/$value/g; } # Remove extra spaces $str2 =~ s/\s+/ /g; # Display the translation print "$str1\n\n-->\n\n$str2\n";

        (Is there anything Perl can’t do?)

        Athanasius <°(((><contra mundum

        To match '.' don't you need to use '\.' or [.] ?

Re: Can't remove directory-Permission denied (-M)
by tye (Sage) on Oct 22, 2012 at 16:50 UTC

    kennethk was right-on when noting that deleting the "." directory is usually a bad idea (and the source of your error message).

    However, for the above code to try to delete ".", I believe that that would mean that D:\TestDelete\Test was declared to-be-deleted by your code (especially for $File::Find::name to be '.' -- my testing shows $_ being '.' when File::Find gets all the way to the top of the directory tree being searched and $File::Find::name never being '.', just FYI).

    That being the case means that the whole use of File::Find is a waste and you could just have done rmtree("D:/TestDelete/Test").

    That leads me to consider the logic behind your code more critically. Deleting directories where the modification time of the directory is more than 2 but less than 4 days in the past is certainly a bit strange.

    Beyond that, you should realize that creating or deleting a file in the foo/bar directory will have no impact on the foo directory's modification time. So you may need to use more sophisticated tests if you want to avoid removing a directory full of files made 2-or-fewer or 4-or-more days ago just because some parent or grand-parent directory was modified during that time window. And, of course, modifying a file has no impact on the containing directory's modification time.

    But you give no real hint at the motivation for the rather strange use of -M so I can't suggest any specific improvements.

    - tye        

Re: Can't remove directory-Permission denied
by aitap (Curate) on Oct 22, 2012 at 15:32 UTC
    In addition to the (++) previous answer, Windows never lets user delete an open file or directory. If the file you want to delete is open, you'll have to terminate the application which holds it open (or make it close the file somehow else).
    Sorry if my advice was wrong.

      Not completely true. Windows applications are free to open files in a manner that specifies that deleting is allowed. It is just a matter of which FILE_SHARE_* constants are specified. I find it unfortunate that the Unix-like interfaces for opening files on Windows specify that renaming and deleting is not to be allowed. I'd prefer that Unix-like calls result in more-Unix-like behavior.

      Win32API::File documents the FILE_SHARE_* constants and allows one to make use of them from Perl. Sadly, I neglected to mention in those documents that FILE_SHARE_DELETE also allows the file to be renamed while it is still open.

      - tye        

Re: Can't remove directory-Permission denied ($^E)
by tye (Sage) on Oct 22, 2012 at 16:57 UTC

    FYI, this is one of the cases where $^E is more informative than $! (on Windows). For this failure, it would report:

    The process cannot access the file because it is being used by another + process

    When writing Perl code that will only be run on Windows, I sometimes report $^E as well as or instead of reporting $!. Most of the time it doesn't matter. But there are a few cases where $^E more accurately points to the real source of the failure.

    - tye        

Re: Can't remove directory-Permission denied
by Lotus1 (Vicar) on Oct 22, 2012 at 17:11 UTC

    After you fix the problem with attempting to remove the directory '.' the next likely problem with this code is the file test -d.

    sub unwanted { if(-d $dir) { if ( ( -M $_ ) >2 &&(-M $_)<4)

    $dir is a directory so this will return true even when $_ is a file. Try the following instead of if(-d $dir):

    return unless -d;

    This will test $_.

Re: Can't remove directory-Permission denied
by Anonymous Monk on Oct 22, 2012 at 14:19 UTC

    Kindly help me.

    With what exactly? Do what?