The shutil.rmtree() is a function belonging to the module shutil
. shutil
, or shell utilities, is a Python module that allows the user to perform advanced operations on system files and a collection of files. This module can automate processes that deal with deletion or copying.
shutil.rmtree() can be used to delete an entire directory tree, which may include sub-folders, sub-directories, and files which come under the tree.
Importing the Module
As of Python 3.10, shutil
it is included in the Python Standard Library under the File and Directory Access category.
import shutil
Function Syntax and Parameters
shutil.rmtree(path, ignore_errors=False, onerror=None)
- path – File path or a path-like object. A path-like objects can be bytes or string representing a file path.
- ignore_errors – If ignore_errors is set to
True
, errors arising due to unsuccessful file removals will be ignored. This is set to False by default - onerror – If ignore_errors is set to False or not specified, the errors which arise are handled by the handler mentioned by onerror. If onerror is no specified, it was raise an exception.
Returns
When all parameters are specified, rmtree() returns a tuple consisting of the handled exception through a callback.
Working of the Function
Let’s look at the capabilities of shutil.rmtree()
.
Deleting Directories within a Parent Folder
Here, We have created a folder and a subfolder which consists of a sample document.
Our objective is to remove the directory ‘Sub Folder’. Here’s how we can do that using shutil.rmtree()
.
import shutil
import os
# Name of the Directory to be deleted
directoryName = "SubFolder"
# Parent folder location
location = "C:/Users/Admin/Desktop"
# Passing parent file location and directory name into os.path.join()
directoryPath = os.path.join(location, directoryName)
# Deleting directory and its contents
shutil.rmtree(directoryPath)
Here’s the output. As you can see, the directory has been removed by the function.
Using the ignore_error Parameter
By setting ignore_error=True
, the function bypasses the errors that arise. It will continue deleting files and avoid files that cause exceptions.
import shutil
import os
# Passing a non existent folder to raise an exception
directoryName = "nonExistentFolder"
location = "C:/Users/Admin/Desktop"
directoryPath = os.path.join(location, directoryName)
# Setting ignore_errors = True
shutil.rmtree(directoryPath, ignore_errors=True)
However, I wouldn’t recommend you set ignore_error=True
just to avoid receiving errors. In situations where you have to handle crucial exceptions, it’s best that you use. onerror
.
Setting Callbacks using onerror.
As we talked about, if you decide that you don’t want Python’s default exception handler to raise exceptions, you can pass ignore_error=True and use callbacks through onerror
.
onerror
Has three parameters that you must satisfy.
- function – Standard user-defined Python function which raises the exception.
- path – Path name passed in function.
- execinfo – Exception information returned by a function called sys.exc_info().
Let’s look at an example piece of code that uses ignore_error
along with onerror
.
import shutil
import os
# Creating a function which handles exceptions arised by files
def exceptionHandler(function, path, exc_info):
print("Exception Handled by callback")
# passing a non existent folder
directoryName = "nonExistentFolder"
location = "C:/Users/Admin/Desktop"
path = os.path.join(location,directoryName)
# setting ignore_errors=False so exception is handled by exceptionHandler
shutil.rmtree(path, ignore_errors=False, onerror=exceptionHandler)
#### Output ####
Exception Handled by callback
shutil.rmtree() Vs os.rmdir()
shutil.rmtree() | os.rmdir() |
---|---|
This function can remove a single file along with its entire directory tree. | This function can remove either a system file or a system directory. |
shutil.rmtree() provides parameters to the user that allows them to handle exceptions on their own | Does not provide such parameters. Exceptions can be handled by try + except blocks. |
Allows the user to create versatile code that automates file deletion processes with relative ease. | Despite allowing the user to perform file deletion operations, it’s not as flexible as shutil.rmtree() |
shutil.rmtree() Access Denied Issue on Windows [Solved]
Running shutil.rmtree()
on files in Windows may cause the following exception:
WindowsError: [Error 5] Access is denied: 'path'
This can be due to the fact that the file which you are trying to delete may be read-only. So the apparent solution is to make sure the files are NOT read-only.
Another solution is to use the onerror
parameter and create an exception handler that allows you to force delete read-only documents. Take a look at the following code.
import os
import stat
import shutil
# defining a function that force removes read only documents
def removeReadOnly(func, path, excinfo):
# Using os.chmod with stat.S_IWRITE to allow write permissions
os.chmod(path, stat.S_IWRITE)
func(path)
# Calling rmtree with onerror callback
shutil.rmtree(top, onerror=removeReadOnly)
Deleting Multiple Directories using rmtree() and glob()
glob()
can provide us with a rundown of multiple directories based on our needs. glob()
can work well with rmtree()
to remove an n number of directories.
import glob
import shutil
# iterating through each directory with the matching characters
for eachPath in glob.glob("Sample_Directories"):
shutil.rmtree(path)
Can you Handle symlinks Using rmtree()?
Unfortunately, you can’t handle symlinks using rmtree()
. The function will raise an IOError exception if did so.
Unable to Delete git Directories Using rmtree()
Git repositories in a system may fail to delete after passing shutil.rmtree() in it.
import shutil
shutil.rmtree('c:/repos/sampleRepo')
##### Output #####
'''
WindowsError: [Error 32] The process cannot access the file because it is being used by another process: 'C:\\repos\\sampleRepo
'''
However, this may not be the actual case.
To solve this, we will import the garbage collection module. We shall .clear_cache() to our git object
import gc
import shutil
gc.collect()
sampleGit.git.clear_cache()
# rmtree should work now
shutil.rmtree('c:/repos/sampleRepo')
This is most likely due to a bug from GitPython’s side.
FAQs on Python shutil.rmtree()
Despite the similarity of rmtree()
and remove()
, rmtree()
and other functions from shutil
module provides the user with much more features such as customized error handling and automation of file operations. The module shutil
provides high-level operations. This is unlike other file management modules.
This module provides the user with high-level file operation functions. We have talked about file/directory deletion but shutil
also provides functions to create archives in .zip or .tar format.
No. A way to find out if any function is async or not is to pass it in simply inspect.iscoroutine()
Conclusion
Hence, We have gone through the shutil
module function that is .rmtree()
and its applications. We demonstrated how the function could be used to delete file directories. Seen how it provides us the ability to handle exceptions our own way. Finally, we’ve solved common function errors.