New Issue: How should 'help' message and metadata be defined for ArgumentParser options/flags etc?

18646, "arezaii", "How should 'help' message and metadata be defined for ArgumentParser options/flags etc?", "2021-10-28T21:46:21Z"

As we continue work on the ArgumentParser library, we would like to allow for help messages to be generated for the user. Other argument parsers have some parameters, typically set at the time the argument is defined, to control the help text and some additional features that may affect the usage string.

For example, Python's argparse has parameters in the add_argument method named help, which is a short string to describe the argument, and metavar, which is used to override the default behavior of using the argument's dest field in the generated help text. (dest is an optional parameter that defaults to what our ArgumentParser calls the name parameter.)

Rust's clap crate has a help method on the Arg struct to set the short help text displayed, in addition to a hidden method to hide the argument from displaying in help. (argparse similarly controls visibility with an enum passed in the help parameter)
(there are many more properties to set for an Arg in clap, more so than either Python or Swift)

Swift's ArgumentParser defines an ArgumentHelp struct with public members:

  • abstract - a short description of the argument
  • discussion - an expanded description of the argument
  • valueName - the alternative name to display for the argument's value in the usage message
  • shouldDisplay - indicates visibility in the help message

When declaring an argument, there is a help argument where values for the ArgumentHelp fields can be populated.

I would propose a way to define the short description, visibility, and alternative display name. This could be done through additional parameters to the addArgument, addOption, addFlag, etc. methods on the argumenParser record. I do not see a need for a separate long description (as discussion) parameter at this time, but feel free to voice support and explain why we need it.

The implementation could look something like this:

proc addArgument(<fields already defined>, help="", visible=true, valueName:?t=none)

where valueName would default to the value of the name parameter, previously defined.

Argument declarations might look like:

var myFiles = parser.addArgument(name="fileNames", numArgs=1.., help="one or more filenames to process");
var developerFlag = parser.addFlag(name="secret-debug", defaultValue=false, visible=false);