Skip to content
Snippets Groups Projects
Commit 489f63b3 authored by Malte Bauch's avatar Malte Bauch
Browse files

Flags are now filtered if they are used already

parent 68340451
No related branches found
No related tags found
1 merge request!284Improve usability and better output formatting for gosndc
Pipeline #99169 failed
...@@ -45,8 +45,6 @@ import ( ...@@ -45,8 +45,6 @@ import (
"github.com/spf13/pflag" "github.com/spf13/pflag"
) )
var suggestions []prompt.Suggest
// PromptCompleter provides completion for a device // PromptCompleter provides completion for a device
type PromptCompleter struct { type PromptCompleter struct {
//NOTE: not too sure about this but for now it should be sufficient //NOTE: not too sure about this but for now it should be sufficient
...@@ -105,32 +103,28 @@ func executeFunc(s string) { ...@@ -105,32 +103,28 @@ func executeFunc(s string) {
} }
} }
func flagVisitor(f *pflag.Flag) {
if !f.Hidden {
suggestions = append(suggestions, prompt.Suggest{Text: "--" + f.Name, Description: f.Usage})
}
}
func (pc *PromptCompleter) cstmCompleter(d prompt.Document) []prompt.Suggest { func (pc *PromptCompleter) cstmCompleter(d prompt.Document) []prompt.Suggest {
// Start with the cobra 'rootCmd' and walk through it // Start with the cobra 'rootCmd' and walk through it
// Reference: https://github.com/stromland/cobra-prompt // Reference: https://github.com/stromland/cobra-prompt
currCmd := rootCmd currCmd := rootCmd
inputSplit := removeFlagsFromInputSlice(strings.Fields(d.CurrentLine())) inputSplit := strings.Fields(d.CurrentLine())
if c, _, err := currCmd.Find(inputSplit); err == nil { inputSplitFiltered, inputFlags := filterFlagSlice(inputSplit)
if c, _, err := currCmd.Find(inputSplitFiltered); err == nil {
currCmd = c currCmd = c
} }
return completionBasedOnCmd(pc, currCmd, inputSplit, d) return completionBasedOnCmd(pc, currCmd, inputSplit, inputFlags, d)
} }
func removeFlagsFromInputSlice(input []string) []string { func filterFlagSlice(input []string) (commandSlice []string, flagSlice []string) {
r := []string{}
for _, in := range input { for _, in := range input {
if !strings.HasPrefix(in, "--") { if !strings.HasPrefix(in, "--") {
r = append(r, in) commandSlice = append(commandSlice, in)
} else {
flagSlice = append(flagSlice, strings.Split(in, "=")[0])
} }
} }
return r return commandSlice, flagSlice
} }
func deviceGetCompletion(c *PromptCompleter, d prompt.Document, inputSplit []string) []prompt.Suggest { func deviceGetCompletion(c *PromptCompleter, d prompt.Document, inputSplit []string) []prompt.Suggest {
...@@ -179,28 +173,28 @@ func deviceGetCompletion(c *PromptCompleter, d prompt.Document, inputSplit []str ...@@ -179,28 +173,28 @@ func deviceGetCompletion(c *PromptCompleter, d prompt.Document, inputSplit []str
return []prompt.Suggest{} return []prompt.Suggest{}
} }
func cobraCommandCompletion(currCmd *cobra.Command, d prompt.Document, loaded []prompt.Suggest) []prompt.Suggest { func cobraCommandCompletion(currCmd *cobra.Command, d prompt.Document, inputFlags []string, loaded []prompt.Suggest) []prompt.Suggest {
suggestions = []prompt.Suggest{}
if len(loaded) > 0 {
suggestions = append(suggestions, loaded...)
}
if currCmd.HasAvailableFlags() { if currCmd.HasAvailableFlags() {
// it would be possible to always show the inherited flags, but i think currCmd.LocalFlags().VisitAll(
// this is currently not necessary. func(f *pflag.Flag) {
// currCmd.InheritedFlags().VisitAll(flagVisitor) if !f.Hidden && !sliceContains(inputFlags, "--"+f.Name) {
currCmd.LocalFlags().VisitAll(flagVisitor) loaded = append(loaded, prompt.Suggest{Text: "--" + f.Name, Description: f.Usage})
}
},
)
} }
for _, cmd := range currCmd.Commands() { for _, cmd := range currCmd.Commands() {
suggestions = append(suggestions, prompt.Suggest{Text: cmd.Name(), Description: cmd.Short}) loaded = append(loaded, prompt.Suggest{Text: cmd.Name(), Description: cmd.Short})
} }
return prompt.FilterHasPrefix(suggestions, d.GetWordBeforeCursor(), true)
return prompt.FilterHasPrefix(loaded, d.GetWordBeforeCursor(), true)
} }
func completionBasedOnCmd(c *PromptCompleter, cmd *cobra.Command, inputSplit []string, d prompt.Document) []prompt.Suggest { func completionBasedOnCmd(c *PromptCompleter, cmd *cobra.Command, inputSplit []string, inputFlags []string, d prompt.Document) []prompt.Suggest {
switch cmd { switch cmd {
case pndUseCmd, pndGetCmd: case pndUseCmd, pndGetCmd:
return cobraCommandCompletion(cmd, d, getPnds()) return cobraCommandCompletion(cmd, d, inputFlags, getPnds())
case commitCmd: case commitCmd:
return getChangesByType(pnd.ChangeState_CHANGE_STATE_PENDING) return getChangesByType(pnd.ChangeState_CHANGE_STATE_PENDING)
case confirmCmd: case confirmCmd:
...@@ -211,7 +205,7 @@ func completionBasedOnCmd(c *PromptCompleter, cmd *cobra.Command, inputSplit []s ...@@ -211,7 +205,7 @@ func completionBasedOnCmd(c *PromptCompleter, cmd *cobra.Command, inputSplit []s
devices, _ := getDevices() devices, _ := getDevices()
return devices return devices
default: default:
return cobraCommandCompletion(cmd, d, []prompt.Suggest{}) return cobraCommandCompletion(cmd, d, inputFlags, []prompt.Suggest{})
} }
} }
......
...@@ -96,3 +96,13 @@ func getChangesByType(cType pnd.ChangeState) []prompt.Suggest { ...@@ -96,3 +96,13 @@ func getChangesByType(cType pnd.ChangeState) []prompt.Suggest {
} }
return completer.SortSuggestionByText(s) return completer.SortSuggestionByText(s)
} }
// sliceContains checks if a slice contains the given item
func sliceContains[T comparable](slice []T, toCompare T) bool {
for _, sliceEntry := range slice {
if sliceEntry == toCompare {
return true
}
}
return false
}
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment