I have a directory containing a large number of files:
a.json
b.dll
c.config
d.exe
...
z.exe
When I cd into this directory and type .\ then press Tab, PowerShell autocompletes the files in this order:
> .\a.json
> .\b.dll
> .\c.config
> .\d.exe
> .\z.exe
because by default, the prompt iterates through all files in the directory alphabetically.
I would like it to instead prompt me with executable files before any others, i.e.:
> .\d.exe
> .\z.exe
> .\a.json
> .\b.dll
> .\c.config
How can I do this?
You need to replace the default PowerShell function that's used for tab completion, the mostly-undocumented
TabExpansion2, the content of which you can obtain by runningget-content function:global:tabexpansion2.Because the content of this function may differ on your system, I'm not going to show it in its entirety, only the pertinent part which is the return of the calculated tab completion possibilities (this is from PowerShell Core 7.3.2 x64 running on Windows 10 21H2 x64):
Both code paths are calling the static
System.Management.Automation.CommandCompletion.CompleteInputmethod, using different versions of that method depending on the arguments passed toTabExpansion2.At this point you might think that we need to delve into the innards of these methods and tweak them to taste, but thankfully that's not the case. We don't actually need to change how
CommandCompletion.CompleteInputworks - we just want to change the order of its suggestions. Since it's already done the hard bit, we just need to do the reordering!Hence, modify
TabCompletion2to the following:It's actually really simple:
Wheremethod to filter theCompletionMatchescollection thatCommandCompletionhas helpfully already populated for us, splitting it into one part containing the found executable matches and the other part containing the remaining matchesWith this updated
TabCompletion2installed into our profile and after reloading said profile via typing.$profileand pressing Enter, typing.\and pressing Tab now yields the desired result: