Try/Catch в PowerShell — руководство и примеры
Кратко
Try/Catch — основной инструмент обработки ошибок в PowerShell. В этой статье вы найдёте понятное объяснение блоков Try, Catch и Finally, практические примеры, распространённые ошибки, альтернативы и контрольные списки для проверки. Подойдёт для разработчиков и инженеров, работающих со скриптами Windows.

Что такое Try/Catch в PowerShell?
Try/Catch — конструкция управления потоком, которая ловит ошибки и исключения во время выполнения скрипта. Её основная задача — предсказуемо обработать ошибки, избежать нежелательного завершения скрипта и выполнить очистку (cleanup).
Ключевые термины в одной строке:
- Try: выполняет код, где может возникнуть ошибка.
- Catch: обрабатывает ошибку, если она возникла в Try.
- Finally: выполняет код гарантированно в конце (независимо от ошибки).
Блок Try
Блок Try содержит код, который может вызвать исключение. Если возникает ошибка типа “terminating” (ошибка-прерывание), выполнение переходит в соответствующий блок Catch. Если ошибка “non-terminating”, по умолчанию Catch не сработает, пока не перевести ошибку в terminating (см. раздел о типах ошибок).
Блок Catch
Блок Catch получает объект ошибки ($_.Exception или $Error[0]) и выполняет логику восстановления, логирования или корректного завершения операции. В Catch можно указывать типы исключений, чтобы обработать разные ошибки по-разному.
Блок Finally
Блок Finally выполняется всегда — независимо от того, произошла ли ошибка. Используйте его для освобождения ресурсов, закрытия подключений или записи финальных логов.
Важно: Catch выполняется только для terminating-ошибок. Для non-terminating ошибок используйте -ErrorAction Stop или меняйте $ErrorActionPreference.
Синтаксис и базовый пример
Ниже — минимальный синтаксис и простой пример, который вы легко вставите в PowerShell ISE (включите запуск от администратора, если нужно).
try {
# Код, который может вызвать ошибку
Write-Host "Это не вызовет исключения."
}
catch [System.Exception] {
# Код обработки ошибки
Write-Host "Произошло исключение: $($_.Exception.Message)"
}
finally {
# Очистка, выполнится в любом случае
Write-Host "Блок Finally выполнен."
}
Ещё один практический пример — перевод non-terminating ошибки в terminating с помощью параметра -ErrorAction:
try {
# Например, Get-Content вернёт non-terminating ошибку, если файла нет
Get-Content "C:\путь\неизвестный_файл.txt" -ErrorAction Stop
}
catch {
Write-Host "Ошибка чтения файла: $($_.Exception.Message)"
}
Типы ошибок в PowerShell
PowerShell различает:
- Terminating (останавливающие) ошибки — останавливают выполнение и попадают в Catch.
- Non-terminating (неостанавливающие) ошибки — продолжают выполнение, но сообщают об ошибке в консоли.
Как работать с non-terminating ошибками:
- Используйте параметр -ErrorAction Stop для конкретной команды.
- Установите $ErrorActionPreference = ‘Stop’ на уровне скрипта (внимательно: повлияет на все команды).
- Альтернатива: проверяйте статус выполнения через -ErrorVariable и $LASTEXITCODE, когда это применимо.
Обработка разных типов исключений
В Catch можно указывать конкретный тип исключения, чтобы разделять логику:
try {
# Код, который может кинуть разные типы исключений
}
catch [System.IO.IOException] {
Write-Host "Проблема с вводом/выводом: $($_.Exception.Message)"
}
catch [System.UnauthorizedAccessException] {
Write-Host "Нет прав доступа: $($_.Exception.Message)"
}
catch {
Write-Host "Другая ошибка: $($_.Exception.Message)"
}Практические приёмы и шаблоны (cheat sheet)
- Перевести одну команду в terminating: Command -ErrorAction Stop
- Логирование полного объекта ошибки: Out-File -FilePath log.txt -Append -InputObject ($_.Exception | Out-String)
- Повторная генерация исключения (rethrow): throw $_
- Захват стека вызовов: $_.Exception.StackTrace
- Использовать -ErrorVariable errVar для сбора ошибок без прерывания
Пример логирования и повторного проброса:
try {
Some-Command -ErrorAction Stop
}
catch {
$_ | Out-File -FilePath "C:\logs\error.log" -Append
throw $_
}Когда Try/Catch не сработает — частые ошибки
- Команда выдаёт non-terminating ошибку и вы забыли -ErrorAction Stop.
- Вы проверяете $Error вместо $_ внутри Catch — $Error содержит историю ошибок, а не текущую ошибку в Catch.
- Использование транзакций или асинхронного кода, где исключения обрабатываются иначе.
- Ловля неверного типа исключения — блок Catch с типом не совпадает с реальным исключением.
Альтернативы и дополнения
- Trap: старый синтаксис для обработки ошибок, действует на уровне функции/скрипта и может пригодиться для совместимости, но Try/Catch читается удобнее.
- -ErrorVariable / $Error: полезно для сбора ошибок без прерывания выполнения.
- Проверка возвращаемых кодов и значений: иногда лучше явно проверять возвращаемое значение, чем полагаться на исключения.
Ментальные модели и эвристики
- Модель: Try = попытка, Catch = аварийная обработка, Finally = уборка.
- Эвристика: переводите в terminating только те команды, которые вы умеете восстанавливать или логировать.
- Не используйте общий Catch для всех ошибок без логирования — это скрывает причину отказа.
Контрольный список для разработчика
- Использованы -ErrorAction Stop там, где ожидаются non-terminating ошибки.
- Для ресурсов есть Finally или явная очистка.
- Логи содержат сообщение и стек ошибок.
- Не подавляются ошибки (не оставлять пустой catch без логов).
- Тесты покрывают сценарии с ошибками.
Критерии приёмки
- Скрипт корректно обрабатывает отсутствие файлов и возвращает понятное сообщение пользователю.
- При возникновении ошибки ресурс закрывается или освобождается.
- Лог содержит достаточную информацию для отладки.
Тестовые сценарии (минимум)
- Отсутствие файла: команда должна перейти в Catch и записать лог.
- Ошибка прав доступа: соответствующий Catch должен вернуть понятное сообщение.
- Успех: блок Finally выполняется и очищает ресурсы.
Примеры отказов и крайние случаи
- Асинхронные операции: PowerShell Background jobs и Runspaces требуют иной обработки ошибок.
- Модули с собственным обработчиком ошибок могут подавлять исключения до уровня вызова.
- Команды из внешних приложений возвращают коды выхода вместо исключений — их нужно обрабатывать отдельно.
Словарь в одной строке
- $ErrorActionPreference — глобальная политика обработки ошибок.
- -ErrorAction Stop — делает команду terminating.
- -ErrorVariable var — сохраняет ошибку в переменную.
- $_ — текущий объект ошибки в блоке Catch.
Безопасность и приватность
- Не записывайте чувствительные данные (пароли, токены) в лог ошибок.
- При логировании ограничьте доступ к файлам логов и используйте ротацию логов.
Итог
Try/Catch — базовый и гибкий механизм для управления ошибками в PowerShell. Понимание разницы между terminating и non-terminating ошибками, использование -ErrorAction и грамотное логирование делают скрипты надёжными и предсказуемыми. Начните с простых примеров, затем добавляйте специфику: типы исключений, повторную генерацию и централизованное логирование.
Полезные ссылки
- Plugin-container.exe: Что это и стоит ли удалять?
- Conhost.exe: Что это и как исправить высокую загрузку CPU
- HydraDM.exe: Что это и стоит ли удалять?
- HsMgr64.exe: Что это и можно ли удалить?
Оставьте комментарий: расскажите, как вы используете try/catch в своих скриптах и какие приёмы оказались полезны.
Похожие материалы
FaceTime с Android и Windows — как подключиться
Оглавление в Google Slides — быстрый гид
nice и renice: управляем приоритетами процессов
Запуск Linux GUI через Bash на Windows 10
Исправить steamclient64.dll — файл не найден