Прежде всего, вы можете явно отловить определенные типы исключений:
$ErrorActionPreference = "Stop"
try {
1/0
}
catch [System.DivideByZeroException] {
$_.Exception.GetType().Name
}
try {
gi "c:\x"
}
catch [System.Management.Automation.ItemNotFoundException] {
$_.Exception.GetType().Name
}
DivideByZeroException
- это просто InnerException RuntimeException
, и теоретически InnerException могут быть бесконечно вложенными:
catch {
$exception = $_.Exception
do {
$exception.GetType().Name
$exception = $exception.InnerException
} while ($exception)
}
НО Вы можете обрабатывать RuntimeException
как особый случай. Даже PowerShell делает это. Посмотрите на первый пример кода. Блок захвата достигается, даже если указан тип исключения inner .
Вы могли бы сделать что-то подобное самостоятельно:
catch {
$exception = $_.Exception
if ($exception -is [System.Management.Automation.RuntimeException] -and $exception.InnerException) {
$exception = $exception.InnerException
}
$exception.GetType().Name
}
ПРИМЕЧАНИЕ , что вам требуется один try-catch для каждой команды, если вы хотите перехватить оба исключения. Иначе 2-й не будет выполнен, если 1-й не пройден. Также вы должны указать от $ErrorActionPreference
до "Stop"
, чтобы перехватывать также не завершающиеся исключения.