I need a way to recursively delete a folder and its children.
Is there a prebuilt tool for this, or do I need to write one?
DEL /S doesn't delete directories.
DELTREE was removed from Windows 2000+
RMDIR or RD if you are using the classic Command Prompt (cmd.exe):
rd /s /q "path"
RMDIR [/S] [/Q] [drive:]path
RD [/S] [/Q] [drive:]path
/S Removes all directories and files in the specified directory in addition to the directory itself. Used to remove a directory tree.
/Q Quiet mode, do not ask if ok to remove a directory tree with /S
If you are using PowerShell you can use Remove-Item (which is aliased to del, erase, rd, ri, rm and rmdir) and takes a -Recurse argument that can be shorted to -r
rd -r "path"
admin:
takeown /r /f folder
cacls folder /c /G "ADMINNAME":F /T
rmdir /s folder
Works for anything including sys files
EDIT: I actually found the best way which also solves file path too long problem as well:
mkdir \empty
robocopy /mir \empty folder
RMDIR [/S] [/Q] [drive:]path
RD [/S] [/Q] [drive:]path
/S Removes all directories and files in the specified directory in addition to the directory itself. Used to remove a directory tree.
/Q Quiet mode, do not ask if ok to remove a directory tree with /S
Go to the path and trigger this command.
rd /s /q "FOLDER_NAME"
/s : Removes the specified directory and all subdirectories including any files. Use /s to remove a tree.
/q : Runs rmdir in quiet mode. Deletes directories without confirmation.
/? : Displays help at the command prompt.
You can install cygwin, which has rm as well as ls etc.
For deleting a directory (whether or not it exists) use the following:
if exist myfolder ( rmdir /s/q myfolder )
rm -r -fo <path>
is the closest you can get in Windows PowerShell. It is the abbreviation of
Remove-Item -Recurse -Force -Path <path>
(more details).
The accepted answer is great, but assuming you have Node installed, you can do this much more precisely with the node library "rimraf", which allows globbing patterns. If you use this a lot (I do), just install it globally.
yarn global add rimraf
then, for instance, a pattern I use constantly:
rimraf .\**\node_modules
or for a one-liner that let's you dodge the global install, but which takes slightly longer for the the package dynamic download:
npx rimraf .\**\node_modules
via Powershell
Remove-Item -Recurse -Force "TestDirectory"
via Command Prompt
https://stackoverflow.com/a/35731786/439130
Try this command:
del /s foldername
rmdir /S /Q %DIRNAME%
rmdir /s dirname
First, let’s review what rm -rf does:
C:\Users\ohnob\things>touch stuff.txt
C:\Users\ohnob\things>rm -rf stuff.txt
C:\Users\ohnob\things>mkdir stuff.txt
C:\Users\ohnob\things>rm -rf stuff.txt
C:\Users\ohnob\things>ls -l
total 0
C:\Users\ohnob\things>rm -rf stuff.txt
There are three scenarios where rm -rf is commonly used where it is expected to return 0:
The specified path does not exist.
The specified path exists and is a directory.
The specified path exists and is a file.
I’m going to ignore the whole permissions thing, but nobody uses permissions or tries to deny themselves write access on things in Windows anyways (OK, that’s meant to be a joke…).
First set ERRORLEVEL to 0 and then delete the path only if it exists, using different commands depending on whether or not it is a directory. IF EXIST does not set ERRORLEVEL to 0 if the path does not exist, so setting the ERRORLEVEL to 0 first is necessary to properly detect success in a way that mimics normal rm -rf usage. Guarding the RD with IF EXIST is necessary because RD, unlike rm -f, will throw an error if the target does not exist.
The following script snippet assumes that DELPATH is prequoted. (This is safe when you do something like SET DELPATH=%1. Try putting ECHO %1 in a .cmd and passing it an argument with spaces in it and see what happens for yourself). After the snippet completes, you can check for failure with IF ERRORLEVEL 1.
: # Determine whether we need to invoke DEL or RD or do nothing.
SET DELPATH_DELMETHOD=RD
PUSHD %DELPATH% 2>NUL
IF ERRORLEVEL 1 (SET DELPATH_DELMETHOD=DEL) ELSE (POPD)
IF NOT EXIST %DELPATH% SET DELPATH_DELMETHOD=NOOP
: # Reset ERRORLEVEL so that the last command which
: # otherwise set it does not cause us to falsely detect
: # failure.
CMD /C EXIT 0
IF %DELPATH_DELMETHOD%==DEL DEL /Q %DELPATH%
IF %DELPATH_DELMETHOD%==RD RD /S /Q %DELPATH%
Point is, everything is simpler when the environment just conforms to POSIX. Or if you install a minimal MSYS and just use that.
Here is what you need to do...
Create a batch file with the following line
RMDIR /S %1
Save your batch file as Remove.bat and put it in C:\windows
Create the following registry key
HKEY_CLASSES_ROOT\Directory\shell\Remove Directory (RMDIR)
Launch regedit and update the default value HKEY_CLASSES_ROOT\Directory\shell\Remove Directory (RMDIR)\default
with the following value
"c:\windows\REMOVE.bat" "%1"
Thats it! Now you can right click any directory and use the RMDIR function
LATE BUT IMPORTANT ANSWER to anyone who is having troubles installing npm packages on windows machine and if you are seeing error saying "rm -rf..." command not found.
You can use the bash cli to run rm command on windows.
for npm users, you can change the npm's config to npm config set script-shell "C:\Program Files\Git\bin\bash.exe" this way if the npm package you are trying to install has a post install script that uses rm -rf command, you will be able to run that rm command without needing to change anything in the npm package or disabling the post install scripts config. (For example, styled-components uses rm command in their post install scripts)
If you want to just use the rm command, you can easily use the bash and pass the arguments.
So yes, you can use the 'rm' command on windows.
As a sidenode:
From the linux version with all subdirs (recursive) + force delete
$ rm -rf ./path
to PowerShell
PS> rm -r -fo ./path
which has the close to same params (just seperated) (-fo is needed, since -f could match different other params)
note:
Remove-Item ALIASE
ri
rm
rmdir
del
erase
rd
in powershell, rm is alias of Remove-Item, so remove a file,
rm -R -Fo the_file
is equivalent to
Remove-Item -R -Fo the_file
if you feel comfortable with gnu rm util, you can the rm util by choco package manager on windows.
install gnu utils in powershell using choco:
choco install GnuWin
finally,
rm.exe -rf the_file
You can install GnuWin32 and use *nix commands natively on windows. I install this before I install anything else on a minty fresh copy of windows. :)
Using Powershell 5.1
get-childitem *logs* -path .\ -directory -recurse | remove-item -confirm:$false -recurse -force
Replace logs with the directory name you want to delete.
get-childitem searches for the children directory with the name recursively from current path (.).
remove-item deletes the result.
USE AT YOUR OWN RISK. INFORMATION PROVIDED 'AS IS'. NOT TESTED EXTENSIVELY.
Right-click Windows icon (usually bottom left) > click "Windows PowerShell (Admin)" > use this command (with due care, you can easily delete all your files if you're not careful):
rd -r -include *.* -force somedir
Where somedir is the non-empty directory you want to remove.
Note that with external attached disks, or disks with issues, Windows sometimes behaves odd - it does not error in the delete (or any copy attempt), yet the directory is not deleted (or not copied) as instructed. (I found that in this case, at least for me, the command given by #n_y in his answer will produce errors like 'get-childitem : The file or directory is corrupted and unreadable.' as a result in PowerShell)
In powershell rm -recurse -force works quite well.
here is what worked for me:
Just try decreasing the length of the path.
i.e :: Rename all folders that lead to such a file to smallest possible names. Say one letter names. Go on renaming upwards in the folder hierarchy.
By this u effectively reduce the path length.
Now finally try deleting the file straight away.
Windows Registry Editor Version 5.00
[HKEY_CLASSES_ROOT\Folder\shell\rmdir\command]
#="cmd.exe /s /c rmdir "%V""
There is also deltree if you're on an older version of windows.
You can learn more about it from here:
SS64: DELTREE - Delete all subfolders and files.
I'm wondering if its possible to determine the ownership of the contents in <VIRTUAL_ENV_ROOT>/lib/python3.8/site-packages.
In some cases it is obvious: The package/subfolder numpy is (most likely) owned by the package numpy on PyPI.
But what if there is a weirdly_named package/subfolder where it isn't obvious, i.e., which doesn't correspond to a package on PyPI with the same name? Is there a way to determine which installed package has created a particular sub path?
Basically I'm looking for the pip equivalent of dpkg -S which can e.g. tell me that the file /etc/X11/Xsession is owned by the apt package x11-common.
For the time being I'm going for a simple zsh/bash alias:
alias pip_inspect_ownership='pip show --files $(pip freeze | grep "==" | cut -d "=" -f 1 | tr "\n" " ") | less'
The idea is:
pip show --files <package> <package> ... lists all the files owned by each package in the list, separated by a package information header.
The sub-expression $(pip freeze | grep "==" | cut -d "=" -f 1 | tr "\n" " ") filters out packages installed in editable mode, and collects the remaining into a list of all packages.
I pipe the result through less so that I can quickly search for ownership of multiple files.
https://docs.aws.amazon.com/lambda/latest/dg/lambda-python-how-to-create-deployment-package.html#python-package-dependencies
Above link helps to build a deployment package for AWS-Lambda. I am planning to build a package to access TensorFlow. After following the steps from AWS documentation zip file is around 110MB and directory size is 330MB.
By using the below commands package size can be reduced:
find -name "*.so" | xargs strip
find -name "*.so*" |xargs strip
find . -name \*pyc -delete
rm -R wheel*
find . -type d -name "tests" -exec rm -rf {} +
Zip package size will be reduced to 90MB and directory size is around 290MB which is still greater than the threshold mentioned by AWS.
I also tried to use the docker to build AWS-Lambda package but, Again size was more than the AWS limit.
https://medium.com/i-like-big-data-and-i-cannot-lie/how-to-create-an-aws-lambda-python-3-6-deployment-package-using-docker-d0e847207dd6
Does anyone have any suggestions/opinions where to find the correct documentation to build the package within the AWS size limit?
Don't build large dependencies into your lambda function. Use lambda layers to carry heavy dependencies. Lots of examples for this now. eg., https://github.com/antonpaquin/Tensorflow-Lambda-Layer
here is what i did before i messed up everything :
i tried to install a package using pip3 , after a long time the download finished and suddenly the error about permission came up because i forgot to use sudo at first and because I didn't want to download the packages again and didn't know where is the pip cache folder is , I did a very stupid thing i changed the permission of the entire python folder in the /usr/bin/ to install package without sudo , after this i tried this :
pip3 install tensorflow
File "/usr/bin/pip3", line 7, in <module>
from pip import main
ImportError: No module named 'pip'
i got these damn error ,
can anybody help me fix this ?
Edit :
here is my sequence of the command i used :
1 - pip3 install tensorflow
-- the error came up
2 - sudo find /usr/lib/python3.5/ -type d -exec chmod 766 {} \;
3 - sudo find /usr/lib/python3.5/ -type f -exec chmod 766 {} \;
First, and foremost, I consider your approach quite unwise. You have now changed the permissions of all files and directories for the owner, the group, and others.
In principle you just needed to ensure that pip3 (by extension, your user-account) would be able write files and directories in a directory owned by root (presumably /usr/lib/python3.5/site-packages). You could have accomplished this by:
sudo chmod o+w /usr/lib/python3.5/site-packages
Alternatively you could have changed the ownership of this folder. IMPORTANT: when doing this kind of thing, be sure to know what you are doing, and don't forget to change everything back as soon as possible. Things can be broken, and security issues can be created.
Now as to a solution to your problem. You have now given the directories the following permissions -rwxrw-rw- (6 = 4 (read) + 2 (write)). However for users, and programs executed on its behalf, to do anything to/from a directory they need the right to execute. For this you should have used 5 instead of 6 (5 = 4 (read) + 1 (execute)). To correct:
sudo find /usr/lib/python3.5/ -type d -exec chmod 755 {} \;
Then, I think that for Python to correctly load compiled libraries (shared-objects or .so files) they should also have these permissions. Judging from my own Python directory I would probably do:
sudo find /usr/lib/python3.5/ -type f -exec chmod 644 {} \;
sudo find /usr/lib/python3.5/ -type f -iname '*.so' -exec chmod 755 {} \;
to set everything back to it's original state.
P.S. I am no expert in pip, so I have no idea what the protocol is to avoid pip from re-downloading upon retrying a failed installation.
I have a file that I suspect was installed by pip.
How can I find which package installed that file?
In other words, I'm looking for a command similar to pacman -Qo filename or dpkg -S filename, but for pip. Does it exist? Or should I use some combination of pip and grep?
In that case, I don't know how to list all the file installed.
You could try with
pip list | tail -n +3 | cut -d" " -f1 | xargs pip show -f | grep "filename"
Then search through the results looking for that file.
You can use a python script like this:
#!/usr/bin/env python
import sys
try:
from pip.utils import get_installed_distributions
except ModuleNotFoundError:
from pip._internal.utils.misc import get_installed_distributions
MYPATH=sys.argv[1]
for dist in get_installed_distributions():
# RECORDs should be part of .dist-info metadatas
if dist.has_metadata('RECORD'):
lines = dist.get_metadata_lines('RECORD')
paths = [l.split(',')[0] for l in lines]
# Otherwise use pip's log for .egg-info's
elif dist.has_metadata('installed-files.txt'):
paths = dist.get_metadata_lines('installed-files.txt')
else:
paths = []
if MYPATH in paths:
print(dist.project_name)
Usage looks like this:
$ python lookup_file.py requests/__init__.py
requests
I wrote a more complete version here, with absolute paths:
https://github.com/nbeaver/pip_file_lookup
Try this!
find_pkg_by_filename(){ for pkg in $(pip list | cut -d" " -f1) ; do if pip show -f "$pkg" | grep "$1" ; then echo "=== Above files found in package $pkg ===" ; fi ; done ; }
find_pkg_by_filename somefilename
Note that if you add -q to the grep, it will exit as soon as there's a match, and then pip will complain about broken pipes.