I'm trying to modify PowerShell's tab completion behavior so that it doesn't just match from the beginning of a word but also allows substring matching
under<TAB>
, PowerShell won't suggest code-understanding
because it doesn't start with under
code-understanding
, file-underlined
, etc.)I've already set up PSReadLine
enhancements for better menu-style completion :
Set-PSReadLineKeyHandler -Key Tab -Function MenuComplete
This improves predictions but still only matches the start of words
Is there a native way in PowerShell 7+ to make TAB
completion match substrings instead of just the start of a word ?
tl;dr
Mathias has provided the crucial pointer:
PowerShell's tab completion (aka command completion) supports wildcard expressions so that - rather than trying to roll a complication custom solution - you can simply prefix your substring with *
; to use your example:
*under
Tab will complete to both code-understanding
and file-underlined
(repeatedly pressing Tab cycles through the matches; with your custom Set-PSReadLineKeyHandler -Key Tab -Function MenuComplete
, all completions will be presented in a menu).
With literal strings, PowerShell's command completion uses prefix matching, i.e. the input string must match the start of commands.
under
Tab behaves like (Get-Command).Name -like 'under*'
, i.e. a trailing *
is implied.Wildcard expressions are matched as such (except that a trailing *
is always implied), and a preceding *
therefore effectively performs substring matching, i.e. the literal part is matched anywhere in command names.
*readl*handler
Tab completes to Get-PSReadLineKeyHandler
, Remove-PSReadLineKeyHandler
, and Set-PSReadLineKeyHandler
.PowerShell (Core) 7 offers a little-known command-completion method based on matching capital letters in command names.
E.g., t-mm
completes Test-ModuleManifest
, but note the following:
The capital of the verb part of the command name (Test
in this example) must be followed by -
Every capital letter must be specified (in order) in order to match a command name; e.g., s-t
completes to Start-Transcript
and Stop-Transcript
, but not to Start-ThreadJob
, because the latter has one additional capital, J
(that is, s-tj
is needed to match it).
This approach can not be combined with wildcards.
Also note that many built-in cmdlets come with superficially similar aliases that use a standardized alias prefix that is defined for each approved verb, e.g. sa
for Start-
, followed by - without an intervening -
- a non-standardized (sequence of) letter(s) for the noun part. E.g., jb
is used to represent the Job
part in Start-Job
.
That is, submitting alias sajb
as-is is an alternative to using capital-based command completion with
s-j
Tab.
To see which alias(es), if any, are defined for a given command, use
Get-Alias -Definition <command-name>
[1] Note that the completion works even with non-approved verbs.