Delete all files and folders but exclude a subfolder
PowershellPowershell Problem Overview
I have a folder where I need to delete all files and folders except a small list of files and folders.
I can already exclude a list of files, but don't see a way to exclude a folder and its contents.
Here is the folder structure:
|-C:\temp
\-C:\temp\somefile.txt
\-C:\temp\someotherfile.txt
| |-C:\temp\foldertodelete
\-C:\temp\foldertodelete\file1.txt
| |-C:\temp\foldertokeep
| \-C:\temp\foldertokeep\file2.txt
I want to keep somefile.txt and the folder foldertokeep and its content.
This is what I have right now:
Get-ChildItem -Path 'C:\temp' -Recurse -exclude somefile.txt | Remove-Item -force -recurse
This really does not delete somefile.txt. Is there a way to exclude folder foldertokeep and its content from the delete list?
Powershell Solutions
Solution 1 - Powershell
Get-ChildItem -Path 'C:\temp' -Recurse -exclude somefile.txt |
Select -ExpandProperty FullName |
Where {$_ -notlike 'C:\temp\foldertokeep*'} |
sort length -Descending |
Remove-Item -force
The -recurse switch does not work properly on Remove-Item (it will try to delete folders before all the child items in the folder have been deleted). Sorting the fullnames in descending order by length insures than no folder is deleted before all the child items in the folder have been deleted.
Solution 2 - Powershell
In PowerShell 3.0 and below, you can try simply doing this:
Remove-Item -recurse c:\temp\* -exclude somefile.txt,foldertokeep
Unless there's some parameter I'm missing, this seems to be doing the trick...
Edit: see comments below, the behavior of Remove-Item has changed after PS3, this solution doesn't seem applicable anymore.
Solution 3 - Powershell
Select everything excluding what needs to be keep and pipe that to a delete command.
Say you have those folders
C:.
├───delme1
│ │ delme.txt
│ │
│ └───delmetoo
├───delme2
├───keepme1
│ keepmetoo.txt
│
└───keepme2
To delete everything but preserve the keepme1 and keepme2 folders.
Get-ChildItem -Exclude keepme1,keepme2 | Remove-Item -Recurse -Force
Other solutions are fine but I found this easy to understand and to remember.
Solution 4 - Powershell
I used the below and just removed -Recurse from the 1st line and it leaves all file and sub folders under the exclude folder list.
Get-ChildItem -Path "PATH_GOES_HERE" -Exclude "Folder1", "Folder2", "READ ME.txt" | foreach ($_) {
"CLEANING :" + $_.fullname
Remove-Item $_.fullname -Force -Recurse
"CLEANED... :" + $_.fullname
}
Solution 5 - Powershell
Yes I know this is an old thread. I couldn't get any of the answers above to work in Powershell 5, so here is what I figured out:
Get-ChildItem -Path $dir -Exclude 'name_to_ignore' |
ForEach-Object {Remove-Item $_ -Recurse }
This moves the -Recurse to Remove-Item instead of where the items are found.
Solution 6 - Powershell
According to MSDN Remove-Item
has a known issue with the -exclude
param. Use this variant instead.
Get-ChildItem * -exclude folderToExclude | Remove-Item
Solution 7 - Powershell
This would also help someone...
Adding a variable for PATH_GOES_HERE that is empty or isn't defined prior can cause a recursive deletion in the user directory (or C:\windows\system32 if the script is ran as admin). I found this out the hard way and had to re-install windows.
Try it yourself! (below will only output the file directories into a test.txt)
Get-ChildItem -Path $dir2 -Recurse -Exclude "Folder1 ", FileName.txt | foreach ($_) {
$_.fullname >> C:\temp\test.txt
}
Solution 8 - Powershell
I ran into this and found a one line command that works for me. It will delete all the folders and files on the directory in question, while retaining anything on the "excluded" list. It also is silent so it won't return an error if some files are read-only or in-use.
@powershell Remove-item C:\Random\Directory\* -exclude "MySpecialFolder", "MySecondSpecialFolder" -force -erroraction 'silentlycontinue'
Solution 9 - Powershell
I used this, that works perfectly for me
Get-ChildItem -Path 'C:\Temp\*' -Recurse | Where-Object {($_.FullName -notlike "*windirstat*") -and ($_.FullName -notlike "C:\Temp\GetFolderSizePortable*")} | Remove-Item -Recurse
Solution 10 - Powershell
If your paths include regex special characters then you need to use the -LiteralPath option which does not allow piping. The correct solution in that case looks like this:
Remove-Item -force -LiteralPath(
Get-ChildItem -Path 'C:\temp' -Recurse -exclude somefile.txt |
Select-Object -ExpandProperty FullName |
Where-Object { $_ -notlike 'C:\temp\foldertokeep*' } |
Sort-Object length -Descending
)
Solution 11 - Powershell
This would also help someone...
Get-ChildItem -Path PATH_GOES_HERE -Recurse -Exclude "Folder1 ", "Folder2", FileName.txt | foreach ($_) {
"CLEANING :" + $_.fullname
Remove-Item $_.fullname -Force -Recurse
"CLEANED... :" + $_.fullname
}
Solution 12 - Powershell
I want get contribution for this idea
- delete all folder and files include hidden folder
$get-childitem -Path D:\path\folder\to\delete* -Force |select-object -Expandproperty Fullname |remove-item -recurse -Confirm:$false -Force
- delete all folder and file include hidden folder but retain exclude folder
$get-childitem -Path D:\path\folder\to\delete* -Exclude nameexludefolder -Force | select-object -Expandproperty Fullname | remove-item -Force
$get-childitem -Path D:\path\folder\to\delete\ -Exclude nameexludefolder -Force | select-object -Expandproperty Fullname | remove-item -Force
first line remain folders, 2nd line remove remain folder