Windows PowerShellのFunction入門 (命名編)

この記事はWindows PowerShellのFunctionの名前に関する基本的な話です

Get-Verb関数や、FunctionもItemとして扱えるという話を聞いて大体記事の内容が予想着く人はこの記事を読む必要はありません


Windows PowerShellの関数はFunctionFilterを使って以下の様に書きます

Function 名前{
    内容;
}

Filter 名前{
    内容;
}

なお、この記事ではFunctionFilterの違いには触れないので以降はFunctionに一本化して話を進めます

PowerShellの関数 (やコマンドレット) には命名規則があり "動詞-名詞" の形をとります

この命名規則を破ってもPowerShellの文法違反にはならず実行は可能ですが、基本的には守るべきです

使用できる動詞も決まっており、Get-Verbで使える動詞とそのグループの一覧を得ることが出来ます

PS> Get-Verb
Verb        Group
----        -----
Add         Common
Clear       Common

(中略)

Unprotect   Security
Use         Other

例えばGet-Verbで得られる一覧にはShowはありますがDisplayはないので、Holle Worldをコンソールに表示する関数は Display-HelloWorld ではなく Show-HelloWorld にすべきです

試しにHello Worldを関数にすると以下の通りです

Function Show-HelloWorld{
    Write-Host "Hello World";
}

その上でPowerShell命名規則によらないコマンド名で関数を実行したい場合、Set-Aliasで関数に別名を与えることが出来ます

PS> Set-Alias -Name 'HelloWorld' -Value 'Show-HelloWorld';
PS> HelloWorld;
Hello World

ちなみに、Windows PowerShelllsdirGet-ChildItemが実行されるのは、予めAliasが設定されているからです

PS> Get-Alias -Definition 'Get-ChildItem';

CommandType     Name                                               Version    Source
-----------     ----                                               -------    ------
Alias           dir -> Get-ChildItem
Alias           gci -> Get-ChildItem
Alias           ls -> Get-ChildItem

関数は既にある関数やコマンドレットにかぶせて同じ名前で上書きすることが出来ます (多重定義ではありません)

試しにコマンドレットのWrite-Hostを何もしない同名の関数で上書きしてみます

PS> Function Write-Host{}
PS> Write-Host 'HelloWorld'; # FunctionのWrite-Hostが実行され、何も表示されない

これで、Write-Hostを実行してもコンソールに文字が表示されることはありません

……困ったことになりました

この場合は上書き対象がコマンドレットだったのでRemove-Item'Function:Write-Host'を消すことでコマンドレットへのWrite-Hostへの上書きを解くことができます

PS> Function Write-Host{}
PS> Write-Host 'Hello World'; # FunctionのWrite-Hostが実行され、何も表示されない
PS> Remove-Item -Path 'Function:Write-Host';
PS> Write-Host 'Hello World'; # コマンドレットのWrite-Hostが実行される
Hello World

FunctionをFunctionで上書きした場合、消しても元のFunctionは戻ってきません

多数のモジュールなどを導入している場合、名前が被らないように注意する必要があります (前述のとおり、PowerShellの関数は接頭辞となる動詞が限定されているので名前が被りがちです)


Remove-Itemで削除できたことで分かる通り、FuctionもItemとしてPowerShell上では処理されています

つまり、New-ItemやGet-ItemなどのItem操作を行うコマンドレットで関数を作成、取得、変更、削除出来ます

PS> New-Item -Path 'Function:Show-HelloWorld' -Value 'Write-Host "Hello World";';
CommandType     Name                                               Version    Source
-----------     ----                                               -------    ------
Function        Show-HelloWorld

PS> Show-HelloWorld;
Hello World

PS> Set-Item -Path 'Function:Show-HelloWorld' -Value 'Write-Host "Hello World!!!"';
PS> Show-HelloWorld;
Hello World!!!

PS> Rename-Item -Path 'Function:Show-HelloWorld' -NewName 'Show-HelloWorld!!!'
PS> Show-HelloWorld!!!;
Hello World!!!

PS> Set-Content -Path 'Function:Show-HelloWorld!!!' -Value 'Write-Host "Hello World!!!`nHello World!!!`nHello World!!!";';
PS> Show-HelloWorld!!!
Hello World!!!
Hello World!!!
Hello World!!!

割とやりたい放題です