Есть ли на самом деле лучший способ обработки ошибок?

#powershell

#powershell

Вопрос:

Я пытаюсь создать новое задание stream analytics с помощью сценария powershell в Azure, следующий фрагмент является частью файла сценария, который добавит службы в группу ресурсов.

пример кода :

 try{
    New-AzureRmStreamAnalyticsJob -ResourceGroupName $resourceGroup -File $template -Name $streamAnalyticsJobName -Force -ErrorAction Stop 
}catch{
    Write-Output $error[0] | Out-File -Append -FilePath $errLogFilePath

}
  

или

 New-AzureRmStreamAnalyticsJob -ResourceGroupName $resourceGroup -File $template -Name $streamAnalyticsJobName -Force -ErrorVariable Errorvalue -ErrorAction SilentlyContinue
Write-Output Errorvalue | Out-File -Append -FilePath $errLogFilePath
  

какой рекомендуемый / наилучший способ документировать ошибки в файле журнала для проверки.

Комментарии:

1. Что бы вы посоветовали сценарию делать с ошибкой? Объективно «наилучшего» способа обработки ошибок не существует, поскольку разные ситуации требуют разных действий по восстановлению. Существует глобальная переменная ErrorActionPreference, которая является поведением по умолчанию, если не указано ErrorAction. Вы также можете использовать операторы trap в качестве глобальных обработчиков ошибок.

2. В обоих ваших примерах вы не обрабатываете никаких ошибок. Вы могли бы также полностью игнорировать блок try / catch и перейти -ErrorAction Stop к вызову и оставить все как есть.

3. @TheIncorrigible1 Это немного отличается. Первый пример, по сути, превращает любую завершающую ошибку в ошибку без завершения. Если бы это было в скрипте, скрипт продолжил бы выполнение. Он также выводит в выходной поток вместо потока ошибок, что в целом не кажется хорошей идеей.

4. @BaconBits Прав, но в любом случае они ничего не обрабатывают .

5. @TheIncorrigible1 В некоторых случаях, преобразование завершающей ошибки в не завершающую ошибку является ее обработкой.

Ответ №1:

  • Ваша 1-я команда также обработает любую завершающую ошибку, выданную New-AzureRmStreamAnalyticsJob , благодаря использованию try / catch .

    • Говоря в целом, если команда имела несколько входных данных и выдавала не завершающиеся ошибки для каждого ввода — это означает, что обработка будет продолжаться по умолчанию, даже после того, как определенный ввод вызовет не завершающуюся ошибку — ваше использование -ErrorAction Stop фактически привело бы к короткому замыканию и прерыванию при обнаружении первой не завершающейся ошибки.
  • В вашей 2-й команде, если бы произошла ошибка завершения, ваше использование -ErrorAction SilentlyContinue было бы не эффективным, и не было бы вашей попытки зафиксировать эту ошибку с помощью -ErrorVariable — короче говоря: общий параметр -ErrorAction влияет только на не завершающиеся ошибки.

В отличие от этого, $ErrorActionPreference переменная предпочтения — удивительно[1]также влияет на то, как обрабатываются ошибки завершения, поэтому, в качестве общего шаблона, вы могли бы использовать следующее, если ваше намерение:

  • продолжить обработку, независимо от того, возникают ли ошибки и являются ли они непрекращающимися или завершающими.
  • разрешить ошибкам возникать автоматически и только записывать их в файл.
   # Silently ignore any subsequent errors, irrespective of severity, but
  # still record them in the automatic $Error collection.
  $ErrorActionPreference = 'SilentlyContinue'

  # Save the current count of errors stored in $Error.
  $errCountBefore = $Error.Count

  New-AzureRmStreamAnalyticsJob -ResourceGroupName $resourceGroup -File $template -Name $streamAnalyticsJobName -Force

  # If errors occurred, append them to a log.
  if ($Error.Count -gt $errCountBefore) {
     $Error[$errCountBefore..($Error.Count-1)] >> $errLogFilePath
  } 
  

[1] Для получения подробного обзора обработки ошибок PowerShell и ее подводных камней см. Этот выпуск GitHub.

Комментарии:

1. Рад это слышать @tuggo; Я только что добавил сноску со ссылкой на полный обзор обработки ошибок PowerShell и ее подводных камней.