fix(history): handle cases where special commands add their command to the stack (#3168)

Fixes #3166

Throughout the code, pushCmd is used for when a command is being executed (switched to) to conditionally add the new command onto the history. The history commands (keybinds `[`, `]`, `-`) only navigate through the stack with indices and therefore should never manipulate the stack -- however with some special commands (specialCmd), navigating to those commands previously unconditionally added the command to the stack unlike "typical" commands like `pods`, `svc`.

Here we pass in the pushCmd boolean to all appropriate special commands so that if the stack should not be manipulated, they do not push their command onto the stack.

The original issue reported issues with Aliases, but there were unreported bugs with Namespaces and Contexts as well. Notably, RBAC commands and Dir commands were not modified as they do not push their command onto the history stack, functioning more as "virtual" commands that will not appear in the history.
mine
tyzbit 2025-03-07 09:32:34 -05:00 committed by GitHub
parent 1e9f85dd15
commit 548536e40d
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
3 changed files with 19 additions and 16 deletions

View File

@ -645,7 +645,7 @@ func (a *App) cowCmd(msg string) {
dialog.ShowError(a.Styles.Dialog(), a.Content.Pages, msg)
}
func (a *App) dirCmd(path string) error {
func (a *App) dirCmd(path string, pushCmd bool) error {
log.Debug().Msgf("DIR PATH %q", path)
_, err := os.Stat(path)
if err != nil {
@ -657,7 +657,9 @@ func (a *App) dirCmd(path string) error {
path = dir
}
}
a.cmdHistory.Push("dir " + path)
if pushCmd {
a.cmdHistory.Push("dir " + path)
}
return a.inject(NewDir(path), true)
}

View File

@ -47,8 +47,9 @@ var (
"help": {},
}
aliasCmd = map[string]struct{}{
"a": {},
"alias": {},
"a": {},
"alias": {},
"aliases": {},
}
xrayCmd = map[string]struct{}{
"x": {},

View File

@ -84,7 +84,7 @@ func allowedXRay(gvr client.GVR) bool {
return ok
}
func (c *Command) contextCmd(p *cmd.Interpreter) error {
func (c *Command) contextCmd(p *cmd.Interpreter, pushCmd bool) error {
ct, ok := p.ContextArg()
if !ok {
return fmt.Errorf("invalid command use `context xxx`")
@ -99,7 +99,7 @@ func (c *Command) contextCmd(p *cmd.Interpreter) error {
return err
}
return c.exec(p, gvr, c.componentFor(gvr, ct, v), true, true)
return c.exec(p, gvr, c.componentFor(gvr, ct, v), true, pushCmd)
}
func (c *Command) namespaceCmd(p *cmd.Interpreter) bool {
@ -115,17 +115,17 @@ func (c *Command) namespaceCmd(p *cmd.Interpreter) bool {
return false
}
func (c *Command) aliasCmd(p *cmd.Interpreter) error {
func (c *Command) aliasCmd(p *cmd.Interpreter, pushCmd bool) error {
filter, _ := p.FilterArg()
gvr := client.NewGVR("aliases")
v := NewAlias(gvr)
v.SetFilter(filter)
return c.exec(p, gvr, v, false, true)
return c.exec(p, gvr, v, false, pushCmd)
}
func (c *Command) xrayCmd(p *cmd.Interpreter) error {
func (c *Command) xrayCmd(p *cmd.Interpreter, pushCmd bool) error {
arg, cns, ok := p.XrayArgs()
if !ok {
return errors.New("invalid command. use `xray xxx`")
@ -148,12 +148,12 @@ func (c *Command) xrayCmd(p *cmd.Interpreter) error {
return err
}
return c.exec(p, client.NewGVR("xrays"), NewXray(gvr), true, true)
return c.exec(p, client.NewGVR("xrays"), NewXray(gvr), true, pushCmd)
}
// Run execs the command by showing associated display.
func (c *Command) run(p *cmd.Interpreter, fqn string, clearStack bool, pushCmd bool) error {
if c.specialCmd(p) {
if c.specialCmd(p, pushCmd) {
return nil
}
gvr, v, err := c.viewMetaFor(p)
@ -233,7 +233,7 @@ func (c *Command) defaultCmd(isRoot bool) error {
return nil
}
func (c *Command) specialCmd(p *cmd.Interpreter) bool {
func (c *Command) specialCmd(p *cmd.Interpreter, pushCmd bool) bool {
switch {
case p.IsCowCmd():
if msg, ok := p.CowArg(); !ok {
@ -246,11 +246,11 @@ func (c *Command) specialCmd(p *cmd.Interpreter) bool {
case p.IsHelpCmd():
_ = c.app.helpCmd(nil)
case p.IsAliasCmd():
if err := c.aliasCmd(p); err != nil {
if err := c.aliasCmd(p, pushCmd); err != nil {
c.app.Flash().Err(err)
}
case p.IsXrayCmd():
if err := c.xrayCmd(p); err != nil {
if err := c.xrayCmd(p, pushCmd); err != nil {
c.app.Flash().Err(err)
}
case p.IsRBACCmd():
@ -260,7 +260,7 @@ func (c *Command) specialCmd(p *cmd.Interpreter) bool {
c.app.Flash().Err(err)
}
case p.IsContextCmd():
if err := c.contextCmd(p); err != nil {
if err := c.contextCmd(p, pushCmd); err != nil {
c.app.Flash().Err(err)
}
case p.IsNamespaceCmd():
@ -268,7 +268,7 @@ func (c *Command) specialCmd(p *cmd.Interpreter) bool {
case p.IsDirCmd():
if a, ok := p.DirArg(); !ok {
c.app.Flash().Errf("Invalid command. Use `dir xxx`")
} else if err := c.app.dirCmd(a); err != nil {
} else if err := c.app.dirCmd(a, pushCmd); err != nil {
c.app.Flash().Err(err)
}
default: