programing

쓰기 오류와슬로우? 종료 중 오류 대 비종단 오류

jooyons 2023. 4. 15. 08:45
반응형

쓰기 오류와슬로우? 종료 중 오류 대 비종단 오류

Posh Code(http://poshcode.org/3226,)의 Get-WebFile 스크립트를 보고 이 기묘한 장치를 발견했습니다.

$URL_Format_Error = [string]"..."
Write-Error $URL_Format_Error
return

그 이유는 무엇입니까?

$URL_Format_Error = [string]"..."
Throw $URL_Format_Error

또는 더 나은 방법:

$URL_Format_Error = New-Object System.FormatException "..."
Throw $URL_Format_Error

제가 알기로는, 비종단 오류는 쓰기 오류를 사용하고, 종료 오류는 슬로우를 사용해야 합니다.따라서 Write-Error 뒤에 Return을 사용하지 않는 것이 좋을 것 같습니다.차이가 있나요?

Write-Error중대하지 않은 오류를 사용자에게 통지하려면 를 사용해야 합니다.기본적으로는 콘솔에 빨간색 텍스트로 오류 메시지를 인쇄하는 작업만 수행합니다.파이프라인이나 루프의 계속은 정지하지 않습니다. Throw한편, 종단 에러라고 불리는 것을 생성합니다.throw를 사용하면 파이프라인 및/또는 전류 루프가 종료됩니다.는 모든 됩니다.trap ★★★try/catch합니다.

주의할 점이 하나 있습니다.설정해서 사용하는 경우Write-Error종료 에러가 발생합니다.

링크된 스크립트에서 다음을 찾을 수 있습니다.

if ($url.Contains("http")) {
       $request = [System.Net.HttpWebRequest]::Create($url)
}
else {
       $URL_Format_Error = [string]"Connection protocol not specified. Recommended action: Try again using protocol (for example 'http://" + $url + "') instead. Function aborting..."
       Write-Error $URL_Format_Error
    return
   }

그 함수의 작성자는 그 함수의 실행을 중지하고 에러 메시지를 화면에 표시하고 싶었지만 스크립트 전체의 실행을 중지하고 싶지는 않았던 것 같습니다.께서 쓰셨을 수도 요.throw 이렇게 '이렇게 하다'라는 돼요.try/catch함수를 호출할 때 사용합니다.

return는 함수, 스크립트 또는 스크립트블록의 현재 범위를 종료합니다.이것은 코드와 함께 가장 잘 설명되어 있습니다.

# A foreach loop.
foreach ( $i in  (1..10) ) { Write-Host $i ; if ($i -eq 5) { return } }

# A for loop.
for ($i = 1; $i -le 10; $i++) { Write-Host $i ; if ($i -eq 5) { return } }

양쪽 출력:

1
2
3
4
5

한는 'Gotcha'를 사용하고 .returnForEach-Object예상대로 처리가 중단되는 일은 없습니다.

상세 정보:

중요:종료 에러에는, 다음의 2 종류가 있습니다.현재 도움말토픽에서는, 유감스럽게도 다음의 토픽이 표시됩니다.

  • 스테이트먼트를 종료하는 에러(특정 회복 불가능한 상황에서의 cmdlet 및 가 나타내는 식에 의해서 보고되는 에러).NET 예외/PS 런타임 에러가 발생하여 스테이트먼트만 종료되고 스크립트 실행은 기본적으로 계속됩니다.

  • 스크립트 종료 오류(보다 정확하게는 runspace-terminating) 또는 실용적으로 말하면 치명적인 오류(기본값)입니다.문장에 의해 트리거되거나 공통 파라미터를 통해 다른 오류 유형 중 하나를 에스컬레이션함으로써 발생합니다.
    -ErrorAction Stop, 또는 프리퍼런스 변수를 경유합니다.$ErrorActionPreference = 'Stop'.
    검출되지 않는 한 현재 runspace(스레드)는 종료됩니다.즉, 현재 스크립트뿐만 아니라 해당하는 경우 모든 발신자도 종료됩니다.

PowerShell의 오류 처리에 대한 포괄적인 개요는 GitHub 문서호 1583을 참조하십시오.

이 투고의 나머지 내용은 비종단 오류와 스테이트먼트 종단 오류에 초점을 맞추고 있습니다.


질문의 핵심에 초점을 맞추어 기존의 유용한 답변을 보완하기 위해:스테이트먼트 종료 오류 또는 비종료 오류를 보고할 것인지 어떻게 선택할 수 있습니까?

Cmdlet 오류 보고서에는 유용한 지침이 포함되어 있습니다. 실용적인 요약을 시도해 보겠습니다.

종료되지 않는 에러의 배후에 있는 일반적인 생각은 큰 입력 세트의 「장애 허용」처리를 가능하게 하는 것입니다.입력 오브젝트의 서브셋을 처리하지 않으면 (디폴트로는) 장기 실행 가능성이 있는 프로세스 전체를 중단해서는 안 됩니다.자동 변수에 수집된 오류 레코드를 통해 보고된 대로 오류를 검사하고 나중에 실패개체 재처리할 수 있습니다.

  • cmdlet/advanced 함수가 다음과 같은 경우 NON-TERMINATINGATING 오류를 보고합니다.

    • 파이프라인 입력 및/또는 배열 값 매개 변수를 통해 여러 입력 개체를 허용하고,
    • 특정 입력 개체에 대해 오류가 발생합니다.
    • 이러한 오류는 원칙적으로 추가 입력 객체의 처리를 방해하지 않습니다(상황상 남은 입력 객체가 없거나 이전 입력 객체가 이미 성공적으로 처리되었을 수 있습니다).
      • 에서는, 「」를 합니다.$PSCmdlet.WriteError()오류를 Write-Error 아쉽게도 ', '불행'은 하지 않습니다$?$FalseGitHub 문제 #3629 참조).
      • 종료되지 않은 오류 처리:$?에 최신 명령어가 적어도1개의 종료되지 않은 오류를 보고했는지 여부를 나타냅니다.
        • thus따는$?존존 $False입력 객체의 (빈) 서브셋이 제대로 처리되지 않았음을 의미할 수 있습니다.아마도 세트 전체가 처리되지 않았을 수 있습니다.
        • 변수 " " "$ErrorActionPreference cmdlet 파라미터 "/" cmdlet """-ErrorAction는, 에러 출력 동작의 관점에서, 비종단 에러의 동작(만)을 변경할 수 있습니다.또, 비종단 에러를 스크립트 종단 에러로 에스컬레이션 할 필요가 있는지를 나타냅니다.
  • 기타 모든 경우 STARTION-TERMINATION-TERMINATING 오류.

    • 특히 SINGLE 또는 NO 입력 오브젝트만 받아들여 NO 또는 SINGLE 출력 오브젝트출력하거나 파라미터 입력만을 취하는 cmdlet/advanced 함수에서 오류가 발생하면 의미 있는 조작을 할 없습니다.
      • 사용하셔야 .$PSCmdlet.ThrowTerminatingError()스테이트먼트 종료 에러를 생성하기 위해서입니다.
      • 와는 대조적으로, '아예'는Throw키워드를 지정하면 스크립트 전체가 중단되는 스크립트 종료 오류가 생성됩니다(기술적으로는 현재 runspace(runspace)).
      • 스테이트먼트 종료 오류 처리:atry/catch 또는 " " "trap스테이트먼트를 사용할 수 있지만(종단 이외의 에러에는 사용할 수 없습니다), 디폴트로는 스테이트먼트를 종단하는 에러라도 스크립트의 나머지 실행은 방해되지 않습니다.종료되지 않는 오류와 마찬가지로$?$False이전 스테이트먼트에서 스테이트먼트 종료 오류가 트리거된 경우.

PowerShell의 모든 핵심 cmdlet이 다음과 같은 규칙을 따르는 것은 아닙니다.

  • (PSV5+)는 파이프라인 입력을 받아들이지 않고 출력 개체를 하나만 생성했는데도 오류가 발생하면 종료되지 않는 오류를 보고합니다. 그러나 적어도 PowerShell [Core] 7.0에서는 수정되었습니다. GitHub 문제 #4634를 참조하십시오.

  • Resume-Job 의 도움말에서는 지원되지 않는 작업 유형(예를 들어 로 작성된 작업)을 전달한다고 합니다.Start-Job왜냐하면Resume-Job워크플로우 작업에만 적용됨)에서 종료 오류가 발생하지만 PSv5.1에서는 그렇지 않습니다.

PowerShell에서 Write-Error cmdlet과 throw 키워드의 주요 차이점은 표준 오류 스트림(stderr)에 일부 텍스트를 인쇄하는 데 반해 실행 중인 명령 또는 함수의 처리를 실제로 종료한다는 것입니다.그런 다음 오류에 대한 정보를 콘솔에 전송하여 PowerShell에서 처리합니다.

이 예에서는, 2개의 다른 동작을 확인할 수 있습니다.

$URL_Format_Error = [string]"..."
Write-Error $URL_Format_Error
return

에서는, 「」를 해 주세요.return콘솔에 오류 메시지가 발송된 후 스크립트 실행을 명시적으로 중지하기 위해 키워드가 추가되었습니다.반면 두 번째 예에서는return으로 「종료」에 의해서 없습니다.throw:

$URL_Format_Error = New-Object System.FormatException "..."
Throw $URL_Format_Error

Andy Arismendi의 답변 추가:

Write-Error가 프로세스를 종료할지 여부는$ErrorActionPreference설정.

비심 스크립팅, 순 하 은 크 우 for non scripts-경,vial의스트tri않$ErrorActionPreference = "Stop"빠른 장애 발생을 위해 권장되는 설정입니다.

"오류에 대한 PowerShell의 기본 동작은 오류 발생 시 계속됩니다.매우 VB6 "On Error Resume Next" (다음 오류 재개 시)-ish"로 느껴집니다.

(http://codebetter.com/jameskovacs/2010/02/25/the-exec-problem/)에서 입수).

그러나 그것은 지 makes however,하,은그만것Write-Error전화를 끊다콜이 종료됩니다.

다른 환경 설정에 관계없이 Write-Error를 종료하지 않는 명령으로 사용하려면 공통 매개 변수를 사용할 수 있습니다. -ErrorAction with value 가치 있게Continue:

 Write-Error "Error Message" -ErrorAction:Continue

Write-Error하면 이 는 에러 를 에러 메시지로 할 수 .-ErrorAction SilentlyContinue (대신)-ea 0) 。throw에는 「」가 합니다.try{...} catch {..}

하려면 라라를 with with with with with with with...를 합니다.Write-Error:

try {
    SomeFunction -ErrorAction Stop
}
catch {
    DoSomething
}

코드 판독이 정확하다면 정답입니다.종료 오류는 다음과 같습니다.throw하고 있는는, 을 참조해 주세요.음음 net 、 NET 타타타 net net 。NET 외 net net

언급URL : https://stackoverflow.com/questions/9294949/when-should-i-use-write-error-vs-throw-terminating-vs-non-terminating-errors

반응형