Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 15 additions & 0 deletions src/GitParamTabExpansion.ps1
Original file line number Diff line number Diff line change
Expand Up @@ -28,12 +28,14 @@ $shortGitParams = @{
rebase = 'm s X S q v n C f i p x'
remote = 'v'
reset = 'q p'
restore = 's p W S q m'
revert = 'e m n S s X'
rm = 'f n r q'
shortlog = 'n s e w'
stash = 'p k u a q'
status = 's b u z'
submodule = 'q b f n N'
switch = 'c C d f m q t'
tag = 'a s u f d v n l m F'
whatchanged = 'p'
}
Expand Down Expand Up @@ -70,13 +72,15 @@ $longGitParams = @{
reflog = 'stale-fix expire= expire-unreachable= all updateref rewrite verbose'
remote = 'verbose'
reset = 'patch quiet soft mixed hard merge keep'
restore = 'source= patch worktree staged quiet progress no-progress ours theirs merge conflict= ignore-unmerged ignore-skip-worktree-bits overlay no-overlay'
revert = 'edit mainline no-edit no-commit gpg-sign signoff strategy= strategy-option continue quit abort'
rm = 'force dry-run cached ignore-unmatch quiet'
shortlog = 'numbered summary email format='
show = 'pretty= format= abbrev-commit no-abbrev-commit oneline encoding= notes no-notes show-notes no-standard-notes standard-notes show-signature'
stash = 'patch no-keep-index keep-index include-untracked all quiet index'
status = 'short branch porcelain long untracked-files ignore-submodules ignored column no-column'
submodule = 'quiet branch force cached files summary-limit remote no-fetch checkout merge rebase init name reference recursive depth'
switch = 'create force-create detach guess no-guess force discard-changes merge conflict= quiet no-progress track no-track orphan ignore-other-worktrees recurse-submodules no-recurse-submodules'
tag = 'annotate sign local-user force delete verify list sort column no-column contains points-at message file cleanup'
whatchanged = 'since'
}
Expand Down Expand Up @@ -149,6 +153,14 @@ $gitParamValues = @{
rebase = @{
strategy = 'resolve recursive octopus ours subtree'
}
restore = @{
conflict = 'merge diff3'
source = {
param($ref)
gitBranches $matches['ref'] $true
gitTags $matches['ref']
}
}
revert = @{
strategy = 'resolve recursive octopus ours subtree'
}
Expand All @@ -161,4 +173,7 @@ $gitParamValues = @{
'untracked-files' = 'no normal all'
'ignore-submodules' = 'none untracked dirty all'
}
switch = @{
conflict = 'merge diff3'
}
}
47 changes: 37 additions & 10 deletions src/GitTabExpansion.ps1
Original file line number Diff line number Diff line change
Expand Up @@ -35,8 +35,8 @@ function script:gitCmdOperations($commands, $command, $filter) {
$script:someCommands = @('add','am','annotate','archive','bisect','blame','branch','bundle','checkout','cherry',
'cherry-pick','citool','clean','clone','commit','config','describe','diff','difftool','fetch',
'format-patch','gc','grep','gui','help','init','instaweb','log','merge','mergetool','mv',
'notes','prune','pull','push','rebase','reflog','remote','rerere','reset','revert','rm',
'shortlog','show','stash','status','submodule','svn','tag','whatchanged', 'worktree')
'notes','prune','pull','push','rebase','reflog','remote','rerere','reset','restore','revert','rm',
'shortlog','show','stash','status','submodule','svn','switch','tag','whatchanged', 'worktree')

$script:gitCommandsWithLongParams = $longGitParams.Keys -join '|'
$script:gitCommandsWithShortParams = $shortGitParams.Keys -join '|'
Expand Down Expand Up @@ -165,6 +165,10 @@ function script:gitCheckoutFiles($GitStatus, $filter) {
gitFiles $filter (@($GitStatus.Working.Unmerged) + @($GitStatus.Working.Modified) + @($GitStatus.Working.Deleted))
}

function script:gitDeleted($GitStatus, $filter) {
gitFiles $filter $GitStatus.Working.Deleted
}

function script:gitDiffFiles($GitStatus, $filter, $staged) {
if ($staged) {
gitFiles $filter $GitStatus.Index.Modified
Expand All @@ -178,8 +182,13 @@ function script:gitMergeFiles($GitStatus, $filter) {
gitFiles $filter $GitStatus.Working.Unmerged
}

function script:gitDeleted($GitStatus, $filter) {
gitFiles $filter $GitStatus.Working.Deleted
function script:gitRestoreFiles($GitStatus, $filter, $staged) {
if ($staged) {
gitFiles $filter (@($GitStatus.Index.Added) + @($GitStatus.Index.Modified) + @($GitStatus.Index.Deleted))
}
else {
gitFiles $filter (@($GitStatus.Working.Unmerged) + @($GitStatus.Working.Modified) + @($GitStatus.Working.Deleted))
}
}

function script:gitAliases($filter) {
Expand Down Expand Up @@ -218,10 +227,16 @@ function script:expandShortParams($cmd, $filter) {
}

function script:expandParamValues($cmd, $param, $filter) {
$gitParamValues[$cmd][$param] -split ' ' |
Where-Object { $_ -like "$filter*" } |
Sort-Object |
ForEach-Object { -join ("--", $param, "=", $_) }
$paramValues = $gitParamValues[$cmd][$param]

$completions = if ($paramValues -is [scriptblock]) {
& $paramValues $filter | Where-Object { $_ -like "$filter*" }
Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Let's bring in fixes from #743

}
else {
$paramValues.Trim() -split ' ' | Where-Object { $_ -like "$filter*" } | Sort-Object
}

$completions | ForEach-Object { -join ("--", $param, "=", $_) }
}

function Expand-GitCommand($Command) {
Expand Down Expand Up @@ -342,6 +357,18 @@ function GitTabExpansionInternal($lastBlock, $GitStatus = $null) {
gitCheckoutFiles $GitStatus $matches['files']
}

# Handles git restore -s <ref> - must come before the next regex case
"^restore.* (?-i)-s\s*(?<ref>\S*)$" {
gitBranches $matches['ref'] $true
gitTags $matches['ref']
break
}

# Handles git restore <path>
"^restore(?:.* (?<staged>(?:(?-i)-S|--staged))|.*) (?<files>\S*)$" {
gitRestoreFiles $GitStatus $matches['files'] $matches['staged']
}

# Handles git rm <path>
"^rm.* (?<index>\S*)$" {
gitDeleted $GitStatus $matches['index']
Expand All @@ -357,8 +384,8 @@ function GitTabExpansionInternal($lastBlock, $GitStatus = $null) {
gitMergeFiles $GitStatus $matches['files']
}

# Handles git checkout <ref>
"^(?:checkout).* (?<ref>\S*)$" {
# Handles git checkout|switch <ref>
"^(?:checkout|switch).* (?<ref>\S*)$" {
& {
gitBranches $matches['ref'] $true
gitRemoteUniqueBranches $matches['ref']
Expand Down
5 changes: 5 additions & 0 deletions test/Get-GitDirectory.Tests.ps1
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,11 @@ Describe 'Get-GitDiretory Tests' {

git init $repoPath
Set-Location $repoPath

# Git rid of Git warnings about configuring user for the commit we do below
git config user.email "you@example.com"
git config user.name "Pester User"

'foo' > .\README.md
git add .\README.md
# Quoting is a hack due to our use of the global:git function and how it converts args for invoke-expression
Expand Down
11 changes: 11 additions & 0 deletions test/TabExpansion.Tests.ps1
Original file line number Diff line number Diff line change
Expand Up @@ -127,6 +127,17 @@ Describe 'TabExpansion Tests' {
}
}

Context 'Restore Source Branch TabExpansion Tests' {
It 'Tab completes source branches -s' {
$result = & $module GitTabExpansionInternal 'git restore -s mas'
$result | Should BeExactly 'master'
}
It 'Tab completes source branches --source=' {
$result = & $module GitTabExpansionInternal 'git restore --source=mas'
$result | Should BeExactly '--source=master'
}
}

Context 'Add/Reset/Checkout TabExpansion Tests' {
BeforeEach {
[System.Diagnostics.CodeAnalysis.SuppressMessageAttribute('PSUseDeclaredVarsMoreThanAssigments', '')]
Expand Down