microsoft / vscode

Visual Studio Code
https://code.visualstudio.com
MIT License
164.33k stars 29.31k forks source link

Better handling (documentation) of background git commands and password prompting #162508

Open thegushi opened 2 years ago

thegushi commented 2 years ago

This could potentially be several separate features, but I want to describe my use case.

I am on a system where we can use GSSAPI (passwordless kerberos authentication, similar to an SSH key), or a password. GSSAPI must be re-initialized periodically by typing a password using a command like kinit to renew your kerberos ticket on your machine. (A similar example, separate from kerberos, may be to consider an ssh agent where the key is periodically removed from the running agent if not used).

Using a password is reasonable on the command line for a single fetch/push. However, in the background, the repeated password failures generated by VSCode cause our security systems to think that a password is being hammered.

The line between where vs code calling git calling ssh are hard to discern here. Setting up a credentials helper does not feel like the correct answer because I do not want to change my behavior when git is used anywhere other than by VS code, when the git command is in the background. (This affects both autofetch and commands invoked by the gui like 'git push'.)

VS Code is already trying to set some kind of git-askpass variable, that is presumably important to it working.

I don't have a good understanding of what environment variables vscode sets in the session before it runs, that I could test on.

Potential solutions:

My full output is:

> git pull --tags origin production
hint: Pulling without specifying how to reconcile divergent branches is
hint: discouraged. You can squelch this message by running one of the following
hint: commands sometime before your next pull:
hint: 
hint:   git config pull.rebase false  # merge (the default strategy)
hint:   git config pull.rebase true   # rebase
hint:   git config pull.ff only       # fast-forward only
hint: 
hint: You can replace "git config" with "git config --global" to set a default
hint: preference for all repositories. You can also pass --rebase, --no-rebase,
hint: or --ff-only on the command line to override the configured default per
hint: invocation.
gushi@redacted.hostname.org: Permission denied (gssapi-with-mic,keyboard-interactive).
fatal: Could not read from remote repository.

Please make sure you have the correct access rights
and the repository exists.
GIT_ASKPASS=/Applications/Visual Studio Code.app/Contents/Resources/app/extensions/git/dist/askpass.sh
VSCODE_GIT_ASKPASS_NODE=/Applications/Visual Studio Code.app/Contents/Frameworks/Code Helper.app/Contents/MacOS/Code Helper
VSCODE_GIT_ASKPASS_EXTRA_ARGS=--ms-enable-electron-run-as-node
VSCODE_GIT_ASKPASS_MAIN=/Applications/Visual Studio Code.app/Contents/Resources/app/extensions/git/dist/askpass-main.js
VSCODE_GIT_IPC_HANDLE=/var/folders/4v/sky46_hn44j24kjdj4d5dnnm0000gn/T/vscode-git-72854b5e68.sock

But I can't find any documentation as to what those things do or how they're used. If they're supposed to be prompting me for a password somehow, they're not doing it. I also cannot tell if the non-interactive terminal used by git fetch has the same options.

The first one is a four line shell script to call a javascript:

#!/bin/sh
VSCODE_GIT_ASKPASS_PIPE=`mktemp`
ELECTRON_RUN_AS_NODE="1" VSCODE_GIT_ASKPASS_PIPE="$VSCODE_GIT_ASKPASS_PIPE" "$VSCODE_GIT_ASKPASS_NODE" "$VSCODE_GIT_ASKPASS_MAIN" $VSCODE_GIT_ASKPASS_EXTRA_ARGS $*
cat $VSCODE_GIT_ASKPASS_PIPE
rm $VSCODE_GIT_ASKPASS_PIPE

The second is a hard-to-read 'webpacked' javascript, clearly [ahem] optimized by removing the pesky whitespace that I'm not going to paste here.

thegushi commented 2 years ago

Speaking specifically to the "GSSAPI" problem, what I'd use if I were writing my own wrapper would be to look at the output of klist, and if it exited non-zero, I'd set PasswordAuthentication no on the command args passed to git.

Because VS code has already shipped with commands, it makes it harder for me to write my own wrapper.

It would be useful if there were a settings knob that allowed me to insert my own "shims" and conditionals, aside from the VS code ones.

gushi@blackfooted-33 ~ % klist
Credentials cache: API:17AD76EA-4C95-4056-B540-F15DDB5573CB
        Principal: gushi@REALM.ORG

  Issued                Expires               Principal
Oct  1 17:01:36 2022  Oct  2 03:01:31 2022  krbtgt/REALM.ORG@REALM.ORG
gushi@blackfooted-33 ~ % echo $?
0
gushi@blackfooted-33 ~ % kdestroy
gushi@blackfooted-33 ~ % klist
klist: Cache not found: API:4491B499-CD15-4327-A6F6-9ABF59C8910D
gushi@blackfooted-33 ~ % echo $?
1
gushi@blackfooted-33 ~ %
thegushi commented 2 years ago

Seriously, just something in the help file that says "How does ssh prompting work with VS Code?" would be better than what's there now.

I don't know the internals (or .js) enough to know what https://github.com/Microsoft/vscode/blob/main/extensions/git/src/askpass.ts does, but it clearly does something with passwords, ssh keys, and known_hosts.