繁体   English   中英

Powershell动态 <tab> 完成

[英]Powershell dynamic <tab> completion

^投票结束之前,请了解上述问题的“答案”是使用另一个模块,而不是您自己如何实现。

我有一组Powershell模块,可用来帮助我进行git工作流程(请考虑gitflow )。

这是一个例子。

Function Merge-FromBranch([string] $branch){
    # ...
}

Set-Alias mfb Merge-FromBranch

我希望能够使用存储库中存在的分支为分支名称完成制表符。

现在获取本地分支名称很容易

> git branch

但是我需要做的是

> mfb fea<tab>

为了在功能分支之间切换。

如何连接它,以便可以在模块上使用Tab键完成$branch参数?

我知道我可以将git branch输出传递给另一个方法( git branch | do-stuff ),但是我不知道如何将其集成到模块的制表符完成中。

为了与posh-git的工作方式保持一致,并制作自己的TabExpansion方法,我现在对自定义命令使用了正确的制表符TabExpansion

# Backup the existing TabExpansion, this will allow us to extend it rather than replace it.
Copy Function:\TabExpansion Function:\OriginalTabExpansion

# Create our own custom TabExpansion method
function TabExpansion($line, $lastWord) {
  $LineBlocks = [regex]::Split($line, '[|;]')
  $lastBlock = $LineBlocks[-1] 

  switch -regex ($lastBlock) {
    #Depends on Posh-Git
    "^$(Get-AliasPattern "mfb|mtb|rb|db|ub|urb|co|pull") (.*)" { gitTabExpansion $lastBlock }
    default { if (Test-Path Function:\OriginalTabExpansion) { OriginalTabExpansion $line $lastWord } }
  }
}

function gitTabExpansion($lastBlock) {
     switch -regex ($lastBlock) {
        "(?<cmd>\S*)$" { gitBranches $matches['cmd'] $true }
    }   
}

function script:gitBranches($filter, $includeHEAD = $false) {
    $prefix = $null
    if ($filter -match "^(?<from>\S*\.{2,3})(?<to>.*)") {
        $prefix = $matches['from']
        $filter = $matches['to']
    }
    $branches = @(git branch --no-color | foreach { if($_ -match "^\*?\s*(?<ref>.*)") { $matches['ref'] } }) +
                @(git branch --no-color -r | foreach { if($_ -match "^  (?<ref>\S+)(?: -> .+)?") { $matches['ref'] } }) +
                @(if ($includeHEAD) { 'HEAD','FETCH_HEAD','ORIG_HEAD','MERGE_HEAD' })
    $branches |
        where { $_ -ne '(no branch)' -and $_ -like "$filter*" } |
        foreach { $prefix + $_ }
}

我不熟悉git branch及其输出。 我希望它只是分支名称,每行一个值,没有任何标题,等等。如果不是,那么您需要修改示例以首先对其进行清理。

如果我相信,这应该适用于PS3 +:

function Merge-FromBranch {

[CmdletBinding()]
Param() 

    DynamicParam {
            # Set the dynamic parameters' name
            $ParameterName = 'Branch'

            # Create the dictionary 
            $RuntimeParameterDictionary = New-Object System.Management.Automation.RuntimeDefinedParameterDictionary

            # Create the collection of attributes
            $AttributeCollection = New-Object System.Collections.ObjectModel.Collection[System.Attribute]

            # Create and set the parameters' attributes
            $ParameterAttribute = New-Object System.Management.Automation.ParameterAttribute
            $ParameterAttribute.Mandatory = $true
            $ParameterAttribute.Position = 1

            # Add the attributes to the attributes collection
            $AttributeCollection.Add($ParameterAttribute)

            # Generate and set the ValidateSet 
            $arrSet = & git branch
            $ValidateSetAttribute = New-Object System.Management.Automation.ValidateSetAttribute($arrSet)

            # Add the ValidateSet to the attributes collection
            $AttributeCollection.Add($ValidateSetAttribute)

            # Create and return the dynamic parameter
            $RuntimeParameter = New-Object System.Management.Automation.RuntimeDefinedParameter($ParameterName, [string], $AttributeCollection)
            $RuntimeParameterDictionary.Add($ParameterName, $RuntimeParameter)
            return $RuntimeParameterDictionary
    }

    begin {
        # Bind the parameter to a friendly variable
        $Branch = $PsBoundParameters[$ParameterName]
    }

    process { Write-Host "Chosen Branch is: $Branch" }

}

修改自的示例: 动态参数中的Dynamic ValidateSet @ blogs.technet.com

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM