Fehlerbehandlung
- Terminierende und nicht-terminierende Fehler unterscheiden
try/catch/finallykorrekt einsetzen- Fehlerinformationen auslesen (
$_,$Error)
Robuste Skripte rechnen damit, dass etwas schiefgeht: Datei fehlt, Server nicht erreichbar, Zugriff verweigert. Fehlerbehandlung bestimmt, was dann passiert.
1. Zwei Arten von Fehlern
Abschnitt betitelt „1. Zwei Arten von Fehlern“PowerShell kennt nicht-terminierende Fehler (Standard bei Cmdlets) und terminierende Fehler.
Get-Content -Path C:\Kurs\gibt-es-nicht.txtWrite-Output "Ich laufe trotzdem weiter."Das Cmdlet meldet einen Fehler in Rot, das Skript macht aber weiter. Das ist ein nicht-terminierender Fehler.
2. -ErrorAction Stop macht den Fehler abfangbar
Abschnitt betitelt „2. -ErrorAction Stop macht den Fehler abfangbar“try { Get-Content -Path C:\Kurs\gibt-es-nicht.txt -ErrorAction Stop}catch { Write-Warning "Datei konnte nicht gelesen werden: $($_.Exception.Message)"}Mit -ErrorAction Stop wird der Fehler terminierend. Innerhalb von catch steht der Fehler in $_.
-ErrorAction |
Wirkung |
|---|---|
Continue |
Standard: Fehler anzeigen, weitermachen |
Stop |
Fehler wird terminierend, catch greift |
SilentlyContinue |
Fehler unterdrücken und weitermachen |
Ignore |
Fehler vollständig ignorieren (nicht in $Error) |
Für ein ganzes Skript setzt du $ErrorActionPreference = 'Stop' an den Anfang. Mach das bewusst und nicht aus Gewohnheit.
3. Aufbau von try/catch/finally
Abschnitt betitelt „3. Aufbau von try/catch/finally“try { $inhalt = Get-Content -Path $Pfad -ErrorAction Stop}catch { Write-Warning "Fehler: $($_.Exception.Message)"}finally { Write-Verbose "Aufräumen, läuft immer."}finally läuft immer, mit oder ohne Fehler. Es ist der Ort für Aufräumarbeiten (Verbindung schließen, Transcript beenden).
4. Bestimmte Fehler gezielt behandeln
Abschnitt betitelt „4. Bestimmte Fehler gezielt behandeln“Welche Art Fehler ist aufgetreten? Frag das Objekt:
try { Get-Item -Path C:\Kurs\gibt-es-nicht.txt -ErrorAction Stop}catch { $_.Exception.GetType().FullName}Das Ergebnis (System.Management.Automation.ItemNotFoundException) setzt du in den catch ein:
try { Get-Item -Path C:\Kurs\gibt-es-nicht.txt -ErrorAction Stop}catch [System.Management.Automation.ItemNotFoundException] { Write-Warning "Pfad existiert nicht."}catch { Write-Warning "Unerwarteter Fehler: $($_.Exception.Message)"}5. Eigene Fehler auslösen
Abschnitt betitelt „5. Eigene Fehler auslösen“if (-not (Test-Path $Pfad)) { throw "Eingabedatei fehlt: $Pfad"}throw erzeugt einen terminierenden Fehler. In Funktionen nutzt du für Parameterfehler besser Write-Error oder Parametervalidierung.
6. Der Fehlerspeicher
Abschnitt betitelt „6. Der Fehlerspeicher“PowerShell sammelt Fehler in $Error. Der neueste steht vorn:
$Error[0]$Error[0] | Format-List * -Force7. Best Practices
Abschnitt betitelt „7. Best Practices“- Fange Fehler dort, wo du sinnvoll reagieren kannst.
- Gib verständliche Meldungen aus: Was wurde versucht, was ist schiefgegangen?
- Verschlucke Fehler nicht stillschweigend (
SilentlyContinueüberall ist ein Anti-Pattern). - Räume im
finallyauf. - Logge Fehler (siehe Logging und Transcripts).
Zusammenfassung
Abschnitt betitelt „Zusammenfassung“try/catchfängt nur terminierende Fehler.-ErrorAction Stopmacht Cmdlet-Fehler terminierend.$_imcatchenthält die Fehlerinformation.finallyläuft immer.- Den Fehlertyp liest du mit
$_.Exception.GetType().FullNameaus.