39
votes

I'm trying to have python delete some directories and I get access errors on them. I think its that the python user account doesn't have rights?

WindowsError: [Error 5] Access is denied: 'path'

is what I get when I run the script.
I've tried

shutil.rmtree  
os.remove  
os.rmdir

they all return the same error.

7
Well, with which user account do you run the script? Usually you should know, at least on your machines and if you set up the script to run ... - Joey
I'm just running it as myself, and I can delete the directly manually, so I'm thinking its a weird windows and python permissions disconnect - DevelopingChris
Try running the script with SysInternals' "Process Monitor" to see exactly which object (file, directory or whatever) the error occurs on and what process it occurs in. "Process Explorer" can tell you what crededtials the process is running under (maybe Process Monitor can too; I'm not sure). - Michael Burr
Would you mind printing out the path you're trying to delete and posting the output here? It could be a problem with the format the path is specified in. - Andre Miller

7 Answers

73
votes

We've had issues removing files and directories on Windows, even if we had just copied them, if they were set to 'readonly'. shutil.rmtree() offers you sort of exception handlers to handle this situation. You call it and provide an exception handler like this:

import errno, os, stat, shutil

def handleRemoveReadonly(func, path, exc):
  excvalue = exc[1]
  if func in (os.rmdir, os.remove) and excvalue.errno == errno.EACCES:
      os.chmod(path, stat.S_IRWXU| stat.S_IRWXG| stat.S_IRWXO) # 0777
      func(path)
  else:
      raise

shutil.rmtree(filename, ignore_errors=False, onerror=handleRemoveReadonly)

You might want to try that.

2
votes

I've never used Python, but I would assume it runs as whatever user executes the script.

2
votes

The scripts have no special user, they just run under the currently logged-in user which executed the script.

Have you tried checking that:

  • you are trying to delete a valid path? and that
  • the path has no locked files?
0
votes

How are you running the script? From an interactive console session? If so, just open up a DOS command window (using cmd) and type 'whoami'. That is who you are running the scripts interactively.

Ok I saw your edits just now...why don't you print the path and check the properties to see if the user account running the scripts has the required privileges?

If whoami does not work on your version of Windows, you may use the environment variables like SET USERNAME and SET DOMAINNAME from your command window.

0
votes

@ThomasH : another brick to the wall.

On unix systems, you have to ensure that parent directory is writeable too. Here is another version :

def remove_readonly(func, path, exc):
    excvalue = exc[1]
    if func in (os.rmdir, os.remove) and excvalue.errno == errno.EACCES:

        # ensure parent directory is writeable too
        pardir = os.path.abspath(os.path.join(path, os.path.pardir))
        if not os.access(pardir, os.W_OK):
            os.chmod(pardir, stat.S_IRWXU| stat.S_IRWXG| stat.S_IRWXO)

        os.chmod(path, stat.S_IRWXU| stat.S_IRWXG| stat.S_IRWXO) # 0777
        func(path)
    else:
        raise
-1
votes

If the script is being run as a scheduled task (which seems likely for a cleanup script), it will probably run as SYSTEM. It's (unwise, but) possible to set permissions on directories so that SYSTEM has no access.

-2
votes

Simple solution after searching for hours is to check first if that folder actually exist!

GIT_DIR="C:/Users/...."
if os.path.exists(GIT_DIR):
    shutil.rmtree(GIT_DIR)

This did the trick for me.