jessevdk/go-flags

Is this the best (or only) way to figure out which subcommands have been used?

Opened this issue · 2 comments

Say I have my app with nested subcommands

App sub1 sub2

In order to check that I have run app sub1 sub2 --someflag I've been using.

if parser.Command.Active.Name  // sub1 {
    if { parser.Command.Active.Active.Name  // sub2 {
        // do something
    }
}

Is that the best way?
I couldn't find anything else in the docs.

I'd like to know this too. I find the documentation/examples are a little lacking here.

For future readers, the best way I found to do this was to use the Commander interface. It's not the most elegant solution, but it works fairly well.

type Options struct {
	Sub1  Subcommand1 `command:"s1"`
	Sub2  Subcommand2 `command:"s2"`
}

type Subcommand1 struct {
	Enabled bool `hidden:"true" no-ini:"true"`
}

// Detect when the subcommand is used.
func (c *Subcommand1) Execute(args []string) error {
	c.Enabled = true
	return nil
}

type Subcommand2 struct {
	Enabled bool `hidden:"true" no-ini:"true"`
}

// Detect when the subcommand is used.
func (c *Subcommand2) Execute(args []string) error {
	c.Enabled = true
	return nil
}

func main() {
	var ops Options
	args, err := flags.Parse(&ops)
	if flags.WroteHelp(err) {
		return
	}
	if err != nil {
		panic(err)
	}

	switch {
	case ops.Sub1.Enabled:
		// do thing 1
	case ops.Sub2.Enabled:
		// do thing 2
	}
}

@jessevdk this would be a good example to provide in your documentation. Additionally, it would be nice if the parser was able to recognize pointer struct types for subcommands; then it would be easy to check if a subcommand was provided with a simple nil check, as demonstrated below:

type Options struct {
	Sub1  *Subcommand1 `command:"s1"`
	Sub2  *Subcommand2 `command:"s2"`
}

type Subcommand1 struct {
	Enabled bool `hidden:"true" no-ini:"true"`
}

type Subcommand2 struct {
	Enabled bool `hidden:"true" no-ini:"true"`
}

func main() {
	var ops Options
	args, err := flags.Parse(&ops)
	if flags.WroteHelp(err) {
		return
	}
	if err != nil {
		panic(err)
	}

	switch {
	case ops.Sub1 != nil:
		// do thing 1
	case ops.Sub2 != nil:
		// do thing 2
	}
}