Skip to content

Commit

Permalink
fix(form): order options by user-defined order
Browse files Browse the repository at this point in the history
  • Loading branch information
Kiyo5hi committed Jul 20, 2023
1 parent 5ac057e commit ae4c13a
Show file tree
Hide file tree
Showing 2 changed files with 54 additions and 35 deletions.
68 changes: 48 additions & 20 deletions pkg/config/form.go
Original file line number Diff line number Diff line change
Expand Up @@ -19,15 +19,17 @@ type OptionValue struct {
Enabled bool
required bool
defaultValue any
index int
name string
}

func (c CLI) Script(f Form) (string, Format) {
return parseScript(&f, c.Command.Name, c.OptionDelim, c.ExplicitBool)
}

func parseScript(f *Form, script string, optionDelim string, explicitBool bool) (string, Format) {
for _, k := range orderedKeys(f.Flags) {
v := f.Flags[k]
as, fs := sortedOptions(f)
for _, v := range fs {
if !v.Enabled {
continue
}
Expand All @@ -41,20 +43,19 @@ func parseScript(f *Form, script string, optionDelim string, explicitBool bool)
switch tv := v.Value.(type) {
case bool:
if explicitBool {
script = fmt.Sprintf("%s %s%s%s%v", script, prefix, k, optionDelim, tv)
script = fmt.Sprintf("%s %s%s%s%v", script, prefix, v.name, optionDelim, tv)
} else {
if !v.Value.(bool) {
continue
}
script = fmt.Sprintf("%s %s%s", script, prefix, k)
script = fmt.Sprintf("%s %s%s", script, prefix, v.name)
}
default:
script = fmt.Sprintf("%s %s%s%s%v", script, prefix, k, optionDelim, tv)
script = fmt.Sprintf("%s %s%s%s%v", script, prefix, v.name, optionDelim, tv)
}
}

for _, k := range orderedKeys(f.Args) {
v := f.Args[k]
for _, v := range as {
if !v.Enabled {
continue
}
Expand All @@ -69,18 +70,6 @@ func parseScript(f *Form, script string, optionDelim string, explicitBool bool)
return parseScript((f.Subcommands)[f.Choice], script, optionDelim, explicitBool)
}

func orderedKeys(m map[string]*OptionValue) []string {
keys := []string{}

for k := range m {
keys = append(keys, k)
}

sort.Strings(keys)

return keys
}

func (c CLI) Form() Form {
f := Form{}

Expand Down Expand Up @@ -119,10 +108,11 @@ func parseForm(c *Command, f *Form) {
required: f.Required,
Enabled: f.Required,
defaultValue: dv,
name: f.Name,
}
}

for _, a := range c.Args {
for i, a := range c.Args {
dv := a.Default
if dv == nil {
// TODO(xinxi.guo): type system has to be enhanced to make use of `Option.Default`, this is a workaround for now
Expand All @@ -137,6 +127,8 @@ func parseForm(c *Command, f *Form) {
required: a.Required,
Enabled: a.Required,
defaultValue: dv,
name: a.Name,
index: i,
}
}

Expand Down Expand Up @@ -179,6 +171,8 @@ func (f Form) Clone() *Form {
Enabled: v.Enabled,
required: v.required,
defaultValue: v.defaultValue,
name: v.name,
index: v.index,
}
}

Expand All @@ -189,6 +183,8 @@ func (f Form) Clone() *Form {
Enabled: v.Enabled,
required: v.required,
defaultValue: v.defaultValue,
name: v.name,
index: v.index,
}
}

Expand All @@ -202,3 +198,35 @@ func (f Form) Clone() *Form {
func (o *OptionValue) ResetValue() {
o.Value = o.defaultValue
}

type optionValueSorter []*OptionValue

func (o optionValueSorter) Len() int {
return len(o)
}

func (o optionValueSorter) Swap(i, j int) {
o[i], o[j] = o[j], o[i]
}

func (o optionValueSorter) Less(i, j int) bool {
return o[i].index >= o[j].index && o[i].name < o[j].name
}

func sortedOptions(f *Form) ([]*OptionValue, []*OptionValue) {
as := []*OptionValue{}
fs := []*OptionValue{}

for _, a := range f.Args {
as = append(as, a)
}

for _, f := range f.Flags {
fs = append(fs, f)
}

sort.Sort(optionValueSorter(as))
sort.Sort(optionValueSorter(fs))

return as, fs
}
21 changes: 6 additions & 15 deletions test/config/form_test.go
Original file line number Diff line number Diff line change
@@ -1,32 +1,23 @@
package config_test

import (
"CLI2UI/pkg/config"
"testing"
)

func TestScriptGeneration(t *testing.T) {
f := docker.Form()

f.Flags["config"] = &config.OptionValue{
Value: "this-config.yaml",
Long: true,
Enabled: true,
}
f.Flags["config"].Enabled = true
f.Flags["config"].Value = "this-config.yaml"

f.Flags["log-level"] = &config.OptionValue{
Value: "info",
Long: true,
Enabled: true,
}
f.Flags["log-level"].Enabled = true
f.Flags["log-level"].Value = "info"

f.Choice = "volume"

f.Subcommands["volume"].Choice = "create"
f.Subcommands["volume"].Subcommands["create"].Args["name"] = &config.OptionValue{
Value: "new-volume",
Enabled: true,
}
f.Subcommands["volume"].Subcommands["create"].Args["name"].Enabled = true
f.Subcommands["volume"].Subcommands["create"].Args["name"].Value = "new-volume"

s, _ := docker.Script(f)

Expand Down

0 comments on commit ae4c13a

Please sign in to comment.