【PowerShell】例外処理(try-catch-finally / throw)

【PowerShell】例外処理(try-catch-finally / throw)

PowerShellのtry-catch-finallyとthrowによる例外処理について記載します。

<環境>
OS:Windows10(64bit)
PSVersion:v5.1

例外処理の基本構文

構文
$ErrorActionPreference = "Stop" # コマンドレットで処理中断

try
{
   # 例外が発生する可能性がある処理(実処理)
}
catch
{
   # 例外が発生した場合の処理(例外処理)
}
finally
{
   # 例外発生の有無に関係なく最後に実行する処理(後処理)
}

  • $ErrorActionPreference = "Stop"
  • "Stop"を設定すると、コマンドレットで例外発生した場合に、処理が中断されてcatch内の処理に移ります。
    デフォルトは"Continue"が設定されているため、コマンドレットで例外発生しても処理が中断されません。

  • try
  • 例外が発生する可能性がある処理を実装します。

  • catch
  • 例外が発生した場合の処理を実装します。
    tryで例外が発生すると処理が中断されて、こちらの処理に移ります。

  • finally
  • 例外発生の有無に関係なく、最後に必ず実行する処理を実装します。(不要なら省略可能)


スクリプト例
$ErrorActionPreference = "Stop"
try
{
    # 存在しないファイル読み込みによる例外発生
    Get-Content -Path "C:\NoExistFile.txt"
}
catch
{
    # 例外出力
    Write-Output $_.Exception.Message
}

catchでの例外出力

例外はcatchの自動変数 ($PSItem または $_)に保持されます。以下に例外出力例を記載します。

$_

例外メッセージと例外発生場所などを出力します。
スクリプト
$ErrorActionPreference = "Stop"
try
{
    Get-Content -Path "C:\NoExistFile.txt"
}
catch
{
    Write-Output $_
}

出力例
Get-Content : パス 'C:\NoExistFile.txt' が存在しないため検出できません。
発生場所 C:\work\test.ps1:4 文字:5
+     Get-Content -Path "C:\NoExistFile.txt"
+     ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : ObjectNotFound: (C:\NoExistFile.txt:String) [Get-Content], ItemNotFoundException
    + FullyQualifiedErrorId : PathNotFound,Microsoft.PowerShell.Commands.GetContentCommand

$_.Exception.Message

例外メッセージを出力します。

スクリプト例
$ErrorActionPreference = "Stop"
try
{
    Get-Content -Path "C:\NoExistFile.txt"
}
catch
{
    Write-Output $_.Exception.Message
}

出力例
パス 'C:\NoExistFile.txt' が存在しないため検出できません。

$_.ScriptStackTrace

例外発生までの呼び出しメソッドを順番に出力します。

スクリプト例
$ErrorActionPreference = "Stop"

function MyGet-Content2
{
    Get-Content -Path "C:\NoExistFile.txt" # 例外発生
}

function MyGet-Content1
{
    MyGet-Content2
}

try
{
    MyGet-Content1
}
catch
{
    Write-Output $_.ScriptStackTrace
}

出力例

MyGet-Content2、C:\work\test.ps1: 行 5
MyGet-Content1、C:\work\test.ps1: 行 10
<ScriptBlock>、C:\work\test.ps1: 行 15

$_.InvocationInfo

例外がスローされたメソッドや例外発生場所、スクリプトに関する追加情報を出力します。

スクリプト例

$ErrorActionPreference = "Stop"
try
{
    Get-Content -Path "C:\NoExistFile.txt"
}
catch
{
    Write-Output $_.InvocationInfo
}

出力例

MyCommand             : Get-Content
BoundParameters       : {}
UnboundArguments      : {}
ScriptLineNumber      : 4
OffsetInLine          : 5
HistoryId             : 8
ScriptName            : C:\work\test.ps1
Line                  :     Get-Content -Path "C:\NoExistFile.txt"
                        
PositionMessage       : 発生場所 C:\work\test.ps1:4 文字:5
                        +     Get-Content -Path "C:\NoExistFile.txt"
                        +     ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
PSScriptRoot          : C:\work
PSCommandPath         : C:\work\test.ps1
InvocationName        : Get-Content
PipelineLength        : 0
PipelinePosition      : 0
ExpectingInput        : False
CommandOrigin         : Internal
DisplayScriptPosition : 

throwステートメントによる例外のスロー

throwステートメントを使用すると例外を意図的にスローすることができます。スローした例外はcatchの自動変数 ($PSItem または $_)に保持されます。

スクリプト例
$ErrorActionPreference = "Stop"
try
{
    # メッセージをスローする
    throw "例外が発生しました。処理を中断します。"
}
catch
{
    Write-Output $_
}

出力例
例外が発生しました。処理を中断します。
発生場所 C:\work\test.ps1:5 文字:5
+     throw "例外が発生しました。処理を中断します。"
+     ~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : OperationStopped: (例外が発生しました。処理を中断します。:String) [], RuntimeException
    + FullyQualifiedErrorId : 例外が発生しました。処理を中断します。


Next Post Previous Post