diff --git a/docs/vctx.md b/docs/vctx.md index 941bb74..f1c072f 100644 --- a/docs/vctx.md +++ b/docs/vctx.md @@ -72,8 +72,8 @@ terminal), and vault's exit code is returned Without colour (piped output, `NO_COLOR`, `table`/`raw`/`pretty` formats) `vctx` execs `vault` exactly as before, so scripts see unchanged output. Streaming or interactive commands (`monitor`, `debug`, `events`, `ssh`, -`agent`, `proxy`, `server`, `login`, `operator`, and `write` to an `auth/` -path, which may prompt for MFA) are always exec'd and never coloured. `JQ_COLORS` +`agent`, `proxy`, `server`, `login`, `operator`, and `write`/`patch`, which +may prompt for MFA) are always exec'd and never coloured. `JQ_COLORS` overrides the JSON palette as in `jq`. ## Flags diff --git a/vctx/main.go b/vctx/main.go index 2828f53..e823e52 100644 --- a/vctx/main.go +++ b/vctx/main.go @@ -17,7 +17,6 @@ import ( "os" "os/exec" "os/signal" - "slices" "strings" "syscall" @@ -37,9 +36,9 @@ var execVault = syscall.Exec var osExit = os.Exit // uncaptured commands are always exec'd: buffering their stdout would hide -// streamed output or prompts (unseal keys, MFA passcodes) until exit, or break -// the TTY, for ssh. -var uncaptured = map[string]bool{"monitor": true, "debug": true, "events": true, "ssh": true, "agent": true, "proxy": true, "server": true, "login": true, "operator": true} +// streamed output or prompts (unseal keys, MFA passcodes; write and patch can +// prompt for MFA) until exit, or break the TTY, for ssh. +var uncaptured = map[string]bool{"monitor": true, "debug": true, "events": true, "ssh": true, "agent": true, "proxy": true, "server": true, "login": true, "operator": true, "write": true, "patch": true} func main() { if err := newRootCmd().Execute(); err != nil { @@ -268,15 +267,12 @@ func colourFormat(args, env []string) string { f = val } f = strings.ToLower(f) - if len(pos) == 0 || uncaptured[pos[0]] || (pos[0] == "write" && slices.ContainsFunc(pos[1:], isAuthPath)) || (f != "json" && f != "yaml") { + if len(pos) == 0 || uncaptured[pos[0]] || (f != "json" && f != "yaml") { return "" } return f } -// isAuthPath matches auth/ paths; a write there may be a login prompting for MFA on stdout. -func isAuthPath(p string) bool { return strings.HasPrefix(strings.TrimPrefix(p, "/"), "auth/") } - // runChild runs vault with stdin/stderr passed through, forwards SIGTERM and // SIGHUP, then writes its captured stdout colourised to w. It returns vault's // exit code, or 128+n if it died from signal n. diff --git a/vctx/main_test.go b/vctx/main_test.go index c999599..a8f2192 100644 --- a/vctx/main_test.go +++ b/vctx/main_test.go @@ -285,10 +285,10 @@ func TestColourFormat(t *testing.T) { {[]string{"-format=yaml", "operator", "generate-root"}, nil, ""}, {[]string{"operator", "rekey", "-format=json"}, nil, ""}, {[]string{"write", "auth/userpass/login/bob"}, []string{"VAULT_FORMAT=json"}, ""}, - {[]string{"write", "-format=json", "auth/x/login/y"}, nil, ""}, - {[]string{"write", "-format", "yaml", "auth/x/login/y", "password=p"}, nil, ""}, - {[]string{"write", "secret/foo", "a=b"}, []string{"VAULT_FORMAT=json"}, "json"}, - {[]string{"write", "-format=json", "secret/foo", "a=b"}, nil, "json"}, + {[]string{"write", "-format=json", "ns1/auth/x/login/y"}, nil, ""}, + {[]string{"write", "-format=json", "secret/foo", "a=b"}, nil, ""}, + {[]string{"patch", "auth/x/config"}, []string{"VAULT_FORMAT=json"}, ""}, + {[]string{"patch", "-format=yaml", "secret/foo", "a=b"}, nil, ""}, } for _, c := range cases { if got := colourFormat(c.args, c.env); got != c.want {