Reputation: 35
I have been writing a script which searches for specific folders within an "Archive" folder and then zips them. Once the folder is successfully zipped I would like it to be deleted.
However, I am running into an issue where the Remove-Item
cmdlet is returning the error "A drive with the name '"E' does not exist" when I use the foreach
command and a variable.
If I run the Remove-Item
command manually with the variable the issue does not occur.
Please let me know why this is happening and what I can do to stop it from happening.
Here is the code:
# Get list of archive folders
$ArchiveFolders = Get-ChildItem \*\*\* |
?{ $_.PSIsContainer } |
Where-Object{ $_.Name -eq "_Archived"} | select FullName
# For each archive folder check which subfolders exist within it
foreach ($folder in $ArchiveFolders) {
(Get-ChildItem $folder.FullName | ?{ $_.PSIsContainer } | select FullName | ConvertTo-Csv -NoTypeInformation) |
Select-Object -Skip 1 |
Add-Content -Path e:\scripts\subfolders.csv
}
# Get list of Subfolders
$ArchiveSubFolders = Get-Content e:\scripts\subfolders.csv
# Select each Subfolder
foreach ($subfolder in $ArchiveSubFolders){
# Move each subfolder to a 7z Archive with the highest compression rate available
$pinfo = New-Object System.Diagnostics.ProcessStartInfo
$pinfo.FileName = "7z.exe"
$pinfo.RedirectStandardError = $true
$pinfo.RedirectStandardOutput = $true
$pinfo.UseShellExecute = $false
$pinfo.Arguments = "a -mx=9 -t7z $subfolder.7z $subfolder"
$p = New-Object System.Diagnostics.Process
$p.StartInfo = $pinfo
$p.Start() | Out-Null
$p.WaitForExit()
# Check Archive was created successfully and then delete the subfolder
if ($p.ExitCode -eq "0") {
Remove-Item -Path $subfolder -Force -Recurse
} else {
Write-Host "$subfolder has not been deleted"
}
}
Upvotes: 2
Views: 1416
Reputation: 200493
PowerShell CSV export/conversion adds double quotes around the fields. Since you read that CSV output via Get-Content
the double quotes are preserved on import, so you get paths "E:\foo"
instead of E:\foo
. This might work for constructing the external command, but it does not work for PowerShell cmdlets, because there is no drive "E:
(with a leading double quote). It's usually a bad idea to make quotes part of the value. You're better off leaving the values without qoutes and adding quotes where they're required.
$ArchiveSubFolders = foreach ($folder in $ArchiveFolders) {
Get-ChildItem $folder.FullName |
Where-Object { $_.PSIsContainer } |
Select-Object -Expand FullName
}
With that said, you don't even need most of your code. You can get the subfolders you want by changing your original path expression to \*\*\*\_Archived\*
and run a single Get-ChildItem
with that. I'd also recommend dropping the System.Diagnostics.Process
approach and use the call operator (&
) instead.
Get-ChildItem '\*\*\*\_Archived\*' | Where-Object {
$_.PSIsContainer
} | Select-Object -Expand FullName | ForEach-Object {
& 7z.exe a -mx=9 -t7z "$_.7z" "$_"
if ($LastExitCode -eq 0) {
Remove-Item -Path $_ -Force -Recurse
} else {
Write-Host "$subfolder has not been deleted"
}
}
Upvotes: 1