Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Broken tab-completion with file or directory names with spaces in the context of tilde-prefixed paths (~) #20851

Open
5 tasks done
mklement0 opened this issue Dec 5, 2023 · 6 comments
Labels
Needs-Triage The issue is new and needs to be triaged by a work group.

Comments

@mklement0
Copy link
Contributor

mklement0 commented Dec 5, 2023

Prerequisites

Steps to reproduce

Note:

The solution is the same on both platforms: preserve the unquoted status of an initial ~ if specified as such.

$null = New-Item -Force "$HOME/a test"

(TabExpansion2 'code ~/a').CompletionMatches[0].CompletionText
(TabExpansion2 'code ~/''a').CompletionMatches[0].CompletionText
(TabExpansion2 'code ~/"a').CompletionMatches[0].CompletionText

# Remove-Item "$HOME/a test" # clean up

Related:

Expected behavior

~/'a test'
~/'a test'
~/"a test"

That is, the unquoted status of the initial ~ should be preserved.

Actual behavior

'~/a test'
'~/a test'
'~/a test'

That is, all expansions resulted in inappropriate quoting in that the previously unquoted ~ - required to trigger PowerShell's tilde-expansion emulation when calling external programs - is now quoted.

Error details

No response

Environment data

PowerShell 7.4.0 on Unix-like platforms.

Visuals

No response

@237dmitry
Copy link

Expected behavior

Quoted part of path also does not work in pwsh with native utilities:

ss

But works with object:

$ $f = gi ~/Desktop/'a test'
$ cat $f
file content

What $f returns to cat, quoted Fullpath or space-escaped Fullpath?

@mklement0
Copy link
Contributor Author

mklement0 commented Dec 5, 2023

Quoted part of path also does not work in pwsh with native utilities:

@237dmitry, yes that's the related bug linked to in the initial post (#20754).

What does $f returns to cat, quoted Fullpath or space-escaped Fullpath?

Neither, because - unlike on Windows - there is no such a thing as a process command line on Unix-like platforms, only an array of verbatim arguments (in the case at hand, it is the value of $f.ToString())

@MartinGC94
Copy link
Contributor

I understand that some (or all) Unix shells have this behavior so I can understand why people would want it to be consistent across the different shells. However, in my eyes the desired behavior seems a bit weird. To me a string is a string, it doesn't matter if you use single quotes, double quotes or no quotes at all, as long as you use whatever escape rules apply to the string type during assignment you are golden.
I can't think of any other example in PowerShell where a string is treated differently, depending on how it was quoted. Can you?

@mklement0
Copy link
Contributor Author

mklement0 commented Feb 12, 2024

@MartinGC94, yes, the distinction should not and does not matter in PowerShell, but PowerShell's emulation of both the tilde expansion and pathname expansion (globbing) when calling external programs on Unix of necessity already does make this distinction:

E.g. printf '~' prints verbatim ~, and printf '*.txt' prints verbatim *.txt - only leaving these arguments unquoted triggers the emulation (as designed).

Similarly, printf '~/Documents' prints verbatim ~/Documents, whereas printf ~/'Documents'prints the equivalent of "$HOME/Documents" - note the of necessity partial quoting, which crucially leaves the ~/ prefix unquoted.

The point of this issue is that if the filename you're tab-completing happens to contain spaces, you end up with a broken command, because the completion quotes the whole argument and therefore deactivates tilde expansion.

(Fixing tab-completion alone isn't enough, however, because even a properly specified / completed argument with spaces, say printf ~/'Folder 1', currently does not trigger tilde expansion, even though it should - see #20754)

@MartinGC94
Copy link
Contributor

Even if it's restricted to native commands it still seems weird to me:
image
Why should I care if "printf" is a native PowerShell command or if it's a native command? PS usually does a good job of making it seamless but here I have to be aware of the type of command.

The point of this issue is that if the filename you're tab-completing happens to contain spaces, you end up with a broken command, because the completion quotes the whole argument and therefore deactivates tilde expansion.

Yeah I understand. Ironically, I did consider just using whatever quotes was used in the input string and just escape the spaces if the string was unquoted because it would be easier to implement but I ended up doing the quoting to match the old behavior.
Also, slightly fun fact: I don't actually use ~ myself, I just added that feature because it seemed simple enough to add and it allowed me add the scaffolding for later adding the variable replacement fix. Lesson learned I guess, even seemingly simple things like a shortcut/alias character can be surprisingly complex.

@mklement0
Copy link
Contributor Author

mklement0 commented Feb 12, 2024

Yes, it is somewhat awkward from a PowerShell perspective, but it is unavoidable when worlds collide, as happens when a different shell's features are emulated.

The emulation - sensibly - only applies to external programs, given that PowerShell commands do their own expansion of ~ and wildcard patterns such as *.txt (where applicable).

If the quoting distinction weren't made, there'd be no way to pass a verbatim ~ or ~/-prefixed argument to an external program.

I see that ~ expansion is now also coming to (calls to external programs) on Windows, as experimental feature PSNativeWindowsTildeExpansion, presumably first available in the next preview, which would be v7.5.0-preview.2
This means that - if it even ever becomes a stable feature - the first stable version it would land in is v7.5 - unfortunately, this is way too late as a fix for #20750

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Needs-Triage The issue is new and needs to be triaged by a work group.
Projects
None yet
Development

No branches or pull requests

3 participants