次の方法で共有


about_Functions_Argument_Completion

簡単な説明

引数の入力候補は、ヒントを提供し、検出を可能にし、引数値の入力入力を高速化する PowerShell の機能です。

詳細な説明

この記事では、PowerShell 関数の引数コンプリートを実装するさまざまな方法について説明します。 引数の完了子は、パラメーターに使用できる値を提供します。 使用可能な値は、ユーザーがパラメーター名の後に Tab キーを押すと実行時に計算されます。 パラメーターの引数の完了を定義するには、いくつかの方法があります。

Note

Tab は、Windows の既定のキー バインドです。 このキーバインドは、PSReadLine モジュールまたは PowerShell をホストしているアプリケーションによって変更できます。 キーバインドは、Windows 以外のプラットフォームでは異なります。 詳細については、「about_PSReadLine」を参照してください。

ValidateSet 属性

ValidateSet属性は、パラメーターまたは変数の有効な値のセットを指定し、タブ補完を有効にします。 パラメーターまたは変数の値がセット内の値と一致しない場合、PowerShell はエラーを生成します。 次の例では、 Fruit パラメーターの値は、 AppleBanana、または Pear のみを指定できます。

Param(
    [Parameter(Mandatory=$true)]
    [ValidateSet('Apple', 'Banana', 'Pear')]
    [string[]]
    $Fruit
)

次の例では、変数 $flavor の値は、 ChocolateStrawberry、または Vanilla である必要があります。 ValidateSet属性は、パラメーターだけでなく、任意の変数で使用できます。

[ValidateSet('Chocolate', 'Strawberry', 'Vanilla')]
[string]$flavor = 'Strawberry'

検証は、スクリプト内でもその変数が割り当てられるたびに発生します。

Param(
    [ValidateSet('hello', 'world')]
    [string]$Message
)

$Message = 'bye'

この例では、実行時に次のエラーが返されます。

MetadataError: The attribute cannot be added because variable Message with
value bye would no longer be valid.

タブ展開の詳細については、「 about_Tab_Expansion」を参照してください。

クラスを使用した動的 ValidateSet 値

Class を使用すると、実行時に ValidateSet の値を動的に生成できます。 次の例では、使用可能なサウンド ファイルの 3 つのファイルシステム パスをチェックする SoundNames という名前の Class を使用して、変数$Soundの有効な値が生成されます。

Class SoundNames : System.Management.Automation.IValidateSetValuesGenerator {
    [string[]] GetValidValues() {
        $SoundPaths = '/System/Library/Sounds/',
                      '/Library/Sounds',
                      '~/Library/Sounds'
        $SoundNames = ForEach ($SoundPath in $SoundPaths) {
            If (Test-Path $SoundPath) {
                (Get-ChildItem $SoundPath).BaseName
            }
        }
        return [string[]] $SoundNames
    }
}

[SoundNames] クラスは、次のように動的な ValidateSet 値として実装されます。

Param(
    [ValidateSet([SoundNames])]
    [string]$Sound
)

Note

IValidateSetValuesGenerator クラスは、PowerShell 6.0 で導入されました。

ArgumentCompletions 属性

ArgumentCompletions 属性を使用すると、タブ補完値を特定のパラメーターに追加できます。 ArgumentCompletions 属性は、タブ補完が必要なパラメーターごとに定義する必要があります。 ArgumentCompletions 属性は、ValidateSet に似ています。 どちらの属性も、ユーザーがパラメーター名の後に Tab を押したときに表示される値の一覧を取得します。 ただし、 ValidateSet とは異なり、値は検証されず、提案に似ています。 したがって、ユーザーはリスト内の値だけでなく、任意の値を指定できます。

ArgumentCompletions 属性は、オプションを定義するためのスクリプト ブロックが必要な ArgumentCompleter 属性と混同しないでください。 指定した値を使用できます

構文は次のとおりです。

function Test-ArgumentCompletions {
    [CmdletBinding()]
    param (
        [Parameter(Mandatory=$true)]
        [ArgumentCompletions('Fruits', 'Vegetables')]
        $Type,

        [Parameter()]
        [ArgumentCompletions('Apple', 'Banana', 'Orange')]
        $Fruit,

        [Parameter()]
        [ArgumentCompletions('Onion', 'Carrot', 'Lettuce')]
        $Vegetable
    )
}

各パラメーターには、タブ補完を有効にする ArgumentCompletions 属性にオプションの一覧が用意されています。

この属性は、PowerShell 6.0 で導入されました。

ArgumentCompleter 属性

ArgumentCompleter 属性を使用すると、タブ補完値を特定のパラメーターに追加できます。 ArgumentCompleter 属性は、タブ補完が必要なパラメーターごとに定義する必要があります。

ArgumentCompleter属性を追加するには、値を決定するスクリプト ブロックを定義する必要があります。 スクリプト ブロックは、次に示す順序で次のパラメーターを受け取る必要があります。 パラメーターの名前は、値が位置指定されるため、関係ありません。

構文は次のとおりです。

function MyArgumentCompleter {
    Param(
        [Parameter(Mandatory)]
        [ArgumentCompleter( {
            param ( $commandName,
                    $parameterName,
                    $wordToComplete,
                    $commandAst,
                    $fakeBoundParameters )
            # Perform calculation of tab completed values here.
        } )]
        $ParamName
    )
}

ArgumentCompleter スクリプト ブロック

スクリプト ブロック パラメーターは、次の値に設定されます。

  • $commandName (位置 0) - このパラメーターは、スクリプト ブロックがタブ補完を提供するコマンドの名前に設定されます。
  • $parameterName (位置 1) - このパラメーターは、タブ補完が必要な値を持つパラメーターに設定されます。
  • $wordToComplete (位置 2) - このパラメーターは、ユーザーが Tab を押す前に指定した値に設定されます。スクリプト ブロックでは、この値を使用してタブ補完値を決定する必要があります。
  • $commandAst (位置 3) - このパラメーターは、現在の入力行の抽象構文ツリー (AST) に設定されます。 詳細については、 AST 型のドキュメントを参照してください。
  • $fakeBoundParameters(位置 4) - このパラメーターは、ユーザーが Tab を押す前に、コマンドレットの$PSBoundParametersを含むハッシュテーブルに設定されます。詳細については、about_Automatic_Variablesを参照してください。

ArgumentCompleter スクリプト ブロックは、パイプライン (ForEach-ObjectWhere-Object、その他の適切なメソッドなど) を使用して値の登録を解除する必要があります。 値の配列を返すと、PowerShell は配列全体をタブ補完値として処理します。

次の例では、 Value パラメーターにタブ補完を追加します。 Value パラメーターのみを指定すると、Value のすべての有効な値または引数が表示されます。 Type パラメーターを指定すると、Value パラメーターには、その型に使用できる値のみが表示されます。

さらに、 -like 演算子により、ユーザーが次のコマンドを入力し、 Tab completion を使用する場合、 Apple のみが返されます。

Test-ArgumentCompleter -Type Fruits -Value A

function MyArgumentCompleter{
    param ( $commandName,
            $parameterName,
            $wordToComplete,
            $commandAst,
            $fakeBoundParameters )

    $possibleValues = @{
        Fruits = @('Apple', 'Orange', 'Banana')
        Vegetables = @('Onion', 'Carrot', 'Lettuce')
    }

    if ($fakeBoundParameters.ContainsKey('Type')) {
        $possibleValues[$fakeBoundParameters.Type] | Where-Object {
            $_ -like "$wordToComplete*"
        }
    } else {
        $possibleValues.Values | ForEach-Object {$_}
    }
}

function Test-ArgumentCompleter {
[CmdletBinding()]
 param (
        [Parameter(Mandatory=$true)]
        [ValidateSet('Fruits', 'Vegetables')]
        $Type,

        [Parameter(Mandatory=$true)]
        [ArgumentCompleter({ MyArgumentCompleter @args })]
        $Value
      )
}

クラス ベースの引数の完了子

PowerShell 7.2 以降では、パラメーター化された引数の完了子のより汎用的な実装を定義できる新機能が追加されました。

ArgumentCompleterAttributeから派生することで、再利用できる汎用のコンプリートを作成できます。次に例を示します。

[DirectoryCompleter(ContainingFile="pwsh.exe", Depth=2)]

[DateCompleter(WeekDay='Monday', From="LastYear")]

[GitCommits(Branch='release')]

派生属性は、 IArgumentCompleterFactory インターフェイスを実装し、プロパティ値を使用して特殊化されたコンプリートを作成する必要があります。

using namespace System.Collections
using namespace System.Collections.Generic
using namespace System.Management.Automation
using namespace System.Management.Automation.Language

class NumberCompleter : IArgumentCompleter {

    [int] $From
    [int] $To
    [int] $Step

    NumberCompleter([int] $from, [int] $to, [int] $step) {
        if ($from -gt $to) {
            throw [ArgumentOutOfRangeException]::new("from")
        }
        $this.From = $from
        $this.To = $to
        $this.Step = $step -lt 1 ? 1 : $step
    }

    [IEnumerable[CompletionResult]] CompleteArgument(
        [string] $CommandName,
        [string] $parameterName,
        [string] $wordToComplete,
        [CommandAst] $commandAst,
        [IDictionary] $fakeBoundParameters) {

        $resultList = [List[CompletionResult]]::new()
        $local:to = $this.To
        $local:step = $this.Step
        for ($i = $this.From; $i -lt $to; $i += $step) {
            $resultList.Add([CompletionResult]::new($i.ToString()))
        }

        return $resultList
    }
}

class NumberCompletionsAttribute : ArgumentCompleterAttribute, IArgumentCompleterFactory {
    [int] $From
    [int] $To
    [int] $Step

    NumberCompletionsAttribute([int] $from, [int] $to, [int] $step) {
        $this.From = $from
        $this.To = $to
        $this.Step = $step
    }

    [IArgumentCompleter] Create() { return [NumberCompleter]::new($this.From, $this.To, $this.Step) }
}

PowerShell からの使用方法は次のようになります。

function Add{
    param(
       [NumberCompletions(0, 100, 5)]
       [int] $X,

       [NumberCompletions(0, 100, 5)]
       [int] $Y
    )
    $X + $Y
}

Register-ArgumentCompleter

Register-ArgumentCompleter コマンドレットは、カスタム引数の完了を登録します。 引数の完了機能を使用すると、指定した任意のコマンドに対して実行時に動的タブ補完を提供できます。

詳細については、「Register-ArgumentCompleter」を参照してください。

関連項目