Why Use Try/Catch in PowerShell?
If you’ve written PowerShell scripts without error handling, you’ve either been extremely lucky or blissfully unaware of the chaos lurking beneath the surface.
Scripts fail.
Networks drop.
Files go missing.
And when things go south, you don’t want your script to just explode—especially if it’s running in production.
Enter Try / Catch, PowerShell’s way of saying, “I got this”. It allows you to gracefully handle errors, log them, and even take corrective action instead of letting your script crash like a house of cards in a strong breeze.
The Basics of Try/Catch
The Try block is where you put the code that might fail. The Catch block is where you handle the failure. Here’s a simple example:
1Try {
2 # Attempting to divide by zero (bad idea)
3 $result = 1 / 0
4} Catch {
5 Write-Host "Oops! Something went wrong: $_"
6}
This will catch the error and print something like:
Oops! Something went wrong: Attempted to divide by zero.
Without Try / Catch, PowerShell would throw a big red error message and stop execution, which is not great if your script is supposed to automate something important—like server deployments or automated maintenance tasks.
Handling Specific Errors
Not all errors are created equal. Sometimes, you want to handle specific exceptions differently. You can do this by specifying an exception type in Catch:
1Try {
2 # Attempting to divide by zero (bad idea)
3 $result = 1 / 0
4} Catch [System.DivideByZeroException]{
5 Write-Host "Oops! Division by zero is never gonna work: $_"
6} Catch {
7 Write-Host "Oops! Something went wrong: $_"
8}
This approach allows you to react differently depending on the type of error. You can probably foresee some exception types, maybe not all!
The Hidden Gotcha: Terminating vs Non-Terminating Errors
PowerShell has two types of errors:
- Terminating errors: These are serious and will stop script execution unless caught.
- Non-terminating errors: These are warnings disguised as errors and won’t trigger a
Catchblock unless you explicitly tell them to.
Take this example:
1Try {
2 Get-Item "C:\NonExistentFile.txt"
3} Catch {
4 Write-Host "Caught that sneaky error!"
5}
Even if the file is non-existant, the Catch is not executed as this is a non-terminating error:
> Get-Item:
> Line |
2 | Get-Item "C:\NonExistentFile.txt"
| ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
| Cannot find path 'C:\NonExistentFile.txt' because it does not exist.
To force PowerShell to treat all errors as terminating (so they can be caught), use $ErrorActionPreference:
1$ErrorActionPreference = "Stop"
2Try {
3 Get-Item "C:\NonExistentFile.txt"
4} Catch {
5 Write-Host "Caught that sneaky error!"
6}
Alternatively, you can use -ErrorAction Stop on a per-command basis:
1Try {
2 Get-Item "C:\NonExistentFile.txt" -ErrorAction Stop
3} Catch {
4 Write-Host "File not found, but at least we caught the error!"
5}
Finally: The Cleanup Crew
Sometimes, you need to clean up resources regardless of whether an error occurred. That’s where Finally comes in:
1Try {
2 $file = [System.IO.StreamWriter]::new("C:\Temp\test.txt")
3 $file.WriteLine("Hello, world!")
4} Catch {
5 Write-Host "Something went wrong."
6} Finally {
7 if ($file) { $file.Close() }
8 Write-Host "Cleanup done!"
9}
The Finally block always runs, making it perfect for cleanup tasks.
Automate Error Handling with Ohlala SmartOps
Writing robust PowerShell scripts with proper error handling is critical for EC2 management—but what if you could skip the scripting and get instant troubleshooting through Microsoft Teams? Check out our guide on PowerShell REST API integration for more automation examples.
Ohlala SmartOps provides AI-powered EC2 management directly in Teams. Instead of writing custom Try/Catch logic for every scenario, ask SmartOps in natural language:
- “Check if my production servers are responding”
- “Restart the IIS service on server X”
- “Show me recent errors from the event log”
SmartOps handles the error checking, logging, and recovery automatically—giving your team 24/7 AI-powered assistance for just $399/month.
Frequently Asked Questions
What’s the difference between terminating and non-terminating errors?
Terminating errors stop script execution and can be caught by Catch blocks. Non-terminating errors are treated as warnings and won’t trigger Catch unless you use -ErrorAction Stop or set $ErrorActionPreference = "Stop".
When should I use Try/Catch vs checking return values?
Use Try/Catch when operations might throw exceptions (file operations, network calls, API requests). Check return values for operations that indicate failure through output (like testing if a file exists with Test-Path).
Do I need -ErrorAction Stop on every command?
No. You can set $ErrorActionPreference = "Stop" at the script level to make all errors terminating. However, using -ErrorAction Stop per command gives you more granular control over which operations should trigger error handling.
What happens if I don’t catch a specific exception type?
PowerShell will execute the first matching Catch block. If you have multiple Catch blocks, put specific exception types first, then a generic Catch block at the end to handle unexpected errors.
Should I always use Finally blocks?
Use Finally when you need to clean up resources (close file handles, database connections, or network streams) regardless of whether an error occurred. If you don’t have cleanup tasks, Finally is optional.
Can I re-throw an error after catching it?
Yes, use the throw keyword inside a Catch block to re-throw the error after logging or handling it. This is useful when you want to log locally but let a higher-level handler deal with the error.
What’s the best way to log errors in production scripts?
Combine Try/Catch with a logging function that writes to files with timestamps and severity levels. For production systems, also consider using Write-EventLog to log errors to Windows Event Viewer for centralized monitoring.
Conclusion
Using Try / Catch in PowerShell isn’t just good practice—it’s a survival skill. It keeps your scripts from failing catastrophically, ensures you can log errors, and allows you to recover gracefully from unexpected issues. So next time you write a script, embrace error handling. Future-you will thank you.
For more details, check out Microsoft’s official documentation:
Related Articles:
- PowerShell Logging Best Practices - Combine error handling with robust logging
- PowerShell REST APIs - Apply error handling to API integrations
- Automating Scheduled Tasks - Build resilient automated workflows
- Managing EC2 with PowerShell - Practical EC2 management examples
Happy scripting!