PowerShell & Scripting
PowerShell-Fehlerbehandlung (Error Handling)
Overview
PowerShell kennt drei Fehlerarten: Nicht terminierende Fehler landen im Fehlerstrom, das Skript läuft weiter (Standard bei Write-Error und vielen Cmdlets). Anweisungsterminierende Fehler stoppen die aktuelle Anweisung, etwa bei .NET-Ausnahmen. Skriptterminierende Fehler brechen die gesamte Aufrufkette ab, zum Beispiel throw oder Fehler mit -ErrorAction Stop.
try/catch fängt nur terminierende Fehler. Damit ein Cmdlet-Fehler im catch-Block ankommt, setzt Du -ErrorAction Stop am Aufruf oder $ErrorActionPreference = 'Stop' für den Gültigkeitsbereich. Mögliche Werte sind Break, Continue (Standard), Ignore, Inquire, SilentlyContinue und Stop.
Native Programme wie robocopy melden Fehler über Exitcodes in $LASTEXITCODE. Seit PowerShell 7.4 gibt es $PSNativeCommandUseErrorActionPreference: Steht die Variable auf $true, erzeugen Exitcodes ungleich 0 Fehler nach $ErrorActionPreference. Standard ist $false.
How it works
Aufbau einer robusten Fehlerbehandlung:
- Riskante Aufrufe in einen try-Block setzen und dort -ErrorAction Stop verwenden.
- Spezifische Ausnahmen zuerst fangen, etwa catch [System.IO.FileNotFoundException], danach allgemeinere Typen. Nur der erste passende catch-Block läuft.
- Im catch-Block steht der Fehler als ErrorRecord in $_ bzw. $PSItem. Für Logs eignen sich $_.ToString(), $_.InvocationInfo (Skript, Zeile) und $_.ScriptStackTrace.
- Der finally-Block läuft immer, ob ein Fehler auftrat oder nicht. Dort gehören Aufräumarbeiten hin, etwa Verbindungen schließen oder Sitzungen trennen.
- Eigene Fehler wirfst Du mit throw oder mit Write-Error -Exception, damit Aufrufer sie nach Typ fangen können.
trap ist ein älterer Mechanismus, der alle Ausnahmen eines Gültigkeitsbereichs abfängt. Er eignet sich für Skripte, die alles protokollieren und weiterlaufen sollen.
Benefits
- Kontrollierte Abbrüche: Skripte stoppen an der richtigen Stelle, statt mit halb verarbeiteten Daten weiterzulaufen
- Sauberes Aufräumen: finally schließt Verbindungen und Sitzungen auch im Fehlerfall, offene Sitzungen blockieren sonst Ressourcen
- Aussagekräftige Logs: Zeilennummer und Stacktrace aus dem ErrorRecord verkürzen die Fehlersuche
- Einheitliche Behandlung von Exitcodes: Mit $PSNativeCommandUseErrorActionPreference fließen native Tools in dieselbe Logik ein
Practical example
Ein Großhändler mit 200 Mitarbeitenden exportiert jede Nacht Artikeldaten per Skript aus dem ERP auf einen SFTP-Server. Bisher lief das Skript bei einem Netzwerkfehler einfach weiter und lieferte leere Dateien aus. Der Admin setzt die kritischen Schritte in try-Blöcke mit -ErrorAction Stop, schreibt Fehler mit Zeilennummer ins Log und schickt eine Meldung an das Ticket-System. Im finally-Block trennt das Skript die Verbindung. Leere Exporte gehören damit der Vergangenheit an.
Things to keep in mind
- -ErrorAction SilentlyContinue nicht pauschal setzen: Fehler verschwinden dann still und fallen erst beim Ergebnis auf
- Exitcodes von robocopy beachten: Werte bis 7 sind informativ, erst ab 8 liegt ein Fehler vor, deshalb lokal $PSNativeCommandUseErrorActionPreference = $false setzen und selbst prüfen
- Spezifische Ausnahmetypen vor Basistypen wie IOException fangen
- In unbeaufsichtigten Skripten jeden catch-Block protokollieren lassen, damit Fehler im Monitoring sichtbar werden
Conclusion
Ohne Fehlerbehandlung sind Automatisierungsskripte ein Risiko, weil sie Fehler verschweigen. try/catch mit -ErrorAction Stop und sauberem Logging gehört in jedes Produktivskript.
Further reading
Related articles
Exchange Online
PowerShell | ExchangeOnlineManagement 3.10.1 Becomes Mandatory
Software Produkte
Disable Microsoft 365 Copilot in the Office apps: Registry, GPO & Intune
Windows Client
Windows 11 Fix | KB5085516 fixed Login-Error
Microsoft Entra ID