Powershell-Test, wenn der Ordner leer ist

71

Wie teste ich in Powershell, ob ein Verzeichnis leer ist?

Oberst Panik
quelle
7
Wer auch immer herabgestimmt hat, hat nicht kommentiert, warum. Upvoting.
RechtschreibungD
@ SpellingD: Ich wünschte, es wäre die ganze Zeit so gewesen. :)
Neolisk

Antworten:

54

Versuche dies...

$directoryInfo = Get-ChildItem C:\temp | Measure-Object
$directoryInfo.count #Returns the count of all of the objects in the directory

Wenn ja $directoryInfo.count -eq 0, ist Ihr Verzeichnis leer.

Boeckm
quelle
8
gciVersteckte Dateien werden standardmäßig nicht angezeigt, daher benötigen Sie den -forceParameter, um sicherzustellen, dass das Verzeichnis wirklich leer ist.
RechtschreibungD
5
Müssen wir jede Datei finden? Dies kann zeitaufwändig sein.
MuiBienCarlota
@SpellingD das wird fehlschlagen, weil ein Ordner wirklich leer ist, aber mit -forcewird die desktop.iniversteckte Systemdatei
auftauchen
1
"directoryInfo.count" gibt NICHT die Anzahl aller Dateien im Verzeichnis zurück, sondern die Anzahl aller Dateien UND Unterverzeichnisse im Verzeichnis. Wenn Sie also 0 Dateien, aber 1 Unterordner haben, wird 1 zurückgegeben.
Benjamin
@ Benjamin aus Gründen der Klarheit bearbeitet. Wenn Sie nur überprüfen möchten, ob sich keine Dateien in einem Verzeichnis befinden, fügen Sie den -fileParameter zu Get-ChildItem hinzu, z. B.$directoryInfo = Get-ChildItem C:\temp -file | Measure-Object
Doktor J
68

Wenn Sie nicht an versteckten oder Systemdateien interessiert sind, können Sie auch Test-Path verwenden

Um festzustellen, ob eine Datei im Verzeichnis vorhanden ist .\temp, können Sie Folgendes verwenden:

Test-Path -Path .\temp\*

oder kurz:

Test-Path .\temp\*
JPBlanc
quelle
3
+1 für eine so ordentliche Art der Überprüfung. Dies sollte als Antwort akzeptiert werden. Übrigens können Sie sogar Test-Path .\temp\*(ohne -Path) auskommen .
Neolisk
Weiß jemand, ob dies immer noch im gesamten Globus wiederholt wird? Oder hört es auf, wenn es auf etwas stößt ?
Kenny
2
Sie sind sich nicht sicher, ob Sie Ihre Frage verstehen, da temporäres Verzeichnis nicht mehr als leer betrachtet wird, wenn es in temp vorhanden ist.
JPBlanc
@ Kenny Es sollte nicht wiederkehren. Es muss nur das einzelne Verzeichnis eingecheckt werden. Es sollte höchstens den gesamten Inhalt davon auflisten.
jpmc26
Sie können auch negieren mit: if (-Not (Test-Path. \ temp *) {}
Clinton Ward
18

Um zu verhindern, dass jede Datei unter c: \ Temp aufgelistet wird (was zeitaufwändig sein kann), können wir Folgendes tun:

if((Get-ChildItem c:\temp\ -force | Select-Object -First 1 | Measure-Object).Count -eq 0)
{
   # folder is empty
}
MuiBienCarlota
quelle
Dies ist bei weitem die schnellste Lösung, da nicht alle Dateien aufgelistet werden und nur bei der ersten gefundenen angehalten wird. Verwenden Sie (Get-ChildItem -LiteralPath 'S:\Test\' -File -Force | Select-Object -First 1 | Measure-Object).Count -ne 0anstelle von, um zu überprüfen, ob Dateien in einem Ordner vorhanden sind Test-Path 'S:\Test\*' -PathType Leaf.
DarkLite1
Measure-Object fügt hier nur dann wirklich etwas hinzu, wenn Sie mit PowerShell v1 arbeiten.
Bacon Bits
4
filter Test-DirectoryEmpty {
    [bool](Get-ChildItem $_\* -Force)
}
Joey
quelle
Warum zum !! ? Danke fürs Erklären!
CB.
Es dient zum Konvertieren des Ergebnisses in einen Booleschen Wert.
Joey
3

Eine Linie:

if( (Get-ChildItem C:\temp | Measure-Object).Count -eq 0)
{
    #Folder Empty
}
Denis Besic
quelle
1

Wenn Sie nur zu JPBlanc hinzufügen und der Verzeichnispfad $ DirPath lautet, funktioniert dieser Code auch für Pfade mit eckigen Klammern.

    # Make square bracket non-wild card char with back ticks
    $DirPathDirty = $DirPath.Replace('[', '`[')
    $DirPathDirty = $DirPathDirty.Replace(']', '`]')

    if (Test-Path -Path "$DirPathDirty\*") {
            # Code for directory not empty
    }
    else {
            # Code for empty directory
    }
Atiq Rahman
quelle
1

Es ist eine Verschwendung, alle Dateien und Verzeichnisse abzurufen und nur zu zählen, um festzustellen, ob das Verzeichnis leer ist. Viel besser .NET zu verwendenEnumerateFileSystemInfos

$directory = Get-Item -Path "c:\temp"
if (!($directory.EnumerateFileSystemInfos() | select -First 1))
{
    "empty"
}
Michael Logutov
quelle
1
#################################################
# Script to verify if any files exist in the Monitor Folder
# Author Vikas Sukhija 
# Co-Authored Greg Rojas
# Date 6/23/16
#################################################


################Define Variables############ 
$email1 = "[email protected]" 
$fromadd = "[email protected]" 
$smtpserver ="mailrelay.conoso.com" 

$date1 = get-date -Hour 1 -Minute 1 -Second 1
$date2 = get-date -Hour 2 -Minute 2 -Second 2 

###############that needs folder monitoring############################ 


$directory = "C:\Monitor Folder"

$directoryInfo = Get-ChildItem $directory | Measure-Object
$directoryInfo.count


if($directoryInfo.Count -gt '0') 
{ 

#SMTP Relay address 
$msg = new-object Net.Mail.MailMessage
$smtp = new-object Net.Mail.SmtpClient($smtpServer) 

#Mail sender 
$msg.From = $fromadd 
#mail recipient 
$msg.To.Add($email1) 
$msg.Subject = "WARNING : There are " + $directoryInfo.count + " file(s) on " + $env:computername +  " in " + " $directory 
$msg.Body = "On " + $env:computername + " files have been discovered in the " + $directory + " folder."
$smtp.Send($msg) 

} 

Else
      { 
    Write-host "No files here" -foregroundcolor Green 
      } 
G Rojas
quelle
3
Obwohl ich Sie auf jeden Fall ermutigen möchte, auf StackOverflow, G, zu posten, gibt es einige "Best Practices", die Sie absichtlich oder auf andere Weise ignorieren. (a) Im Allgemeinen sollten Sie nicht einfach ohne Erklärung eine Postleitzahl eingeben. (b) Sie sollten nicht dieselbe Antwort von einer anderen Person erneut veröffentlichen (Ihre wurde mindestens zweimal gegeben, wenn Sie hier durch die Antworten scrollen). (c) Sie sollten nicht eine ganze Reihe von Code ohne Bezug einschließen - 90% Ihres Codes sind für die gestellte Frage irrelevant. Ich werde nicht abstimmen, sondern wollte nur, dass Sie vorbereitet sind, falls Sie einige Abstimmungen sehen.
Michael Sorens
1

Einfacher Ansatz

if (-Not (Test-Path .\temp*) 
{
 #do your stuff here
} 

Sie können entfernen, -Notwenn Sie das 'if' eingeben möchten, wenn Dateien vorhanden sind

Clinton Ward
quelle
1

Beispiel zum Entfernen eines leeren Ordners:

IF ((Get-ChildItem "$env:SystemDrive\test" | Measure-Object).Count -eq 0) {
    remove-Item "$env:SystemDrive\test" -force
}
Maciej
quelle
1
Bitte schreiben Sie Ihre Antwort auf Englisch, da Stack Overflow eine englische Site ist .
Am 5.
1
    $contents = Get-ChildItem -Path "C:\New folder"
    if($contents.length -eq "") #If the folder is empty, Get-ChileItem returns empty string
    {
        Remove-Item "C:\New folder"
        echo "Empty folder. Deleted folder"
    }
    else{
    echo "Folder not empty"
    }
Yash
quelle
1
#Define Folder Path to assess and delete
$Folder = "C:\Temp\Stuff"

#Delete All Empty Subfolders in a Parent Folder
Get-ChildItem -Path $Folder -Recurse -Force | Where-Object { $_.PSIsContainer -and (Get-ChildItem -Path $_.FullName -Recurse -Force | Where-Object { !$_.PSIsContainer }) -eq $null } | Remove-Item -Force -Recurse

#Delete Parent Folder if empty
If((Get-ChildItem -Path $Folder -force | Select-Object -First 1 | Measure-Object).Count -eq 0) {Remove-Item -Path $CATSFolder -Force -Recurse}
Martureo Martus
quelle
Wenn Sie -Path $_.FullNameGet-ChildItem verwenden, können hier ernsthafte Probleme auftreten . Bitte benutze -LiteralPath !!!
it3xl
0

Das Abrufen einer Zählung von Get-ChildItem kann zu falschen Ergebnissen führen, da ein leerer Ordner oder ein Fehler beim Zugriff auf einen Ordner zu einer Zählung von 0 führen kann.

Ich suche nach leeren Ordnern, um Fehler zu trennen:

Try { # Test if folder can be scanned
   $TestPath = Get-ChildItem $Path -ErrorAction SilentlyContinue -ErrorVariable MsgErrTest -Force | Select-Object -First 1
}
Catch {}
If ($MsgErrTest) { "Error accessing folder" }
Else { # Folder can be accessed or is empty
   "Folder can be accessed"
   If ([string]::IsNullOrEmpty($TestPath)) { # Folder is empty
   "   Folder is empty"
   }
}

Der obige Code versucht zuerst, auf den Ordner zuzugreifen. Wenn ein Fehler auftritt, wird ausgegeben, dass ein Fehler aufgetreten ist. Wenn kein Fehler aufgetreten ist, geben Sie an, dass auf "Ordner kann zugegriffen werden", und überprüfen Sie als nächstes, ob er leer ist.

Michael Yuen
quelle
0

Nachdem ich einige der vorhandenen Antworten untersucht und ein wenig experimentiert hatte, kam ich zu folgendem Ansatz:

function Test-Dir-Valid-Empty {
    param([string]$dir)
    (Test-Path ($dir)) -AND ((Get-ChildItem -att d,h,a $dir).count -eq 0)
}

Dies wird zuerst nach einem gültigen Verzeichnis suchen ( Test-Path ($dir)). Es wird dann prüfen , für Inhalte , einschließlich aller Verzeichnisse, versteckte Datei oder „normale“ Dateien ** aufgrund der Attribute d, hund a, respectively.

Die Verwendung sollte klar genug sein:

PS C_\> Test-Dir-Valid-Empty projects\some-folder
False 

...oder alternativ:

PS C:\> if(Test-Dir-Valid-Empty projects\some-folder){ "empty!" } else { "Not Empty." }
Not Empty.

** Eigentlich bin ich nicht 100% sicher, was der definierte Effekt von ahier ist, aber es führt auf jeden Fall dazu, dass alle Dateien enthalten sind. Die Dokumentation besagt, dass ahversteckte Dateien angezeigt werden, und ich glaube , dass Systemdateien angezeigt werden assollten, also schätze ich, dass aallein nur "normale" Dateien angezeigt werden. Wenn Sie es aus der obigen Funktion entfernen, werden auf jeden Fall versteckte Dateien gefunden, andere jedoch nicht.

Kjartan
quelle
0

Mit dieser Methode .GetFileSystemInfos().Countkönnen Sie die Anzahl der Verzeichnisse überprüfen. Microsoft Docs

$docs = Get-ChildItem -Path .\Documents\Test
$docs.GetFileSystemInfos().Count
Alex_P
quelle