Daniel Alder
Daniel Alder

Reputation: 5372

Understanding arity=ZERO and unnamed arguments in spring shell

I'm using spring-shell 3.3.3 in spring boot, and have the following code:

@Command
public class ExperimentCommand {

  @Command(command = "experiment", description = "Loads a bunch of files from a folder")
  @SuppressWarnings("java:S107")
  public String experiment(
      @Option(longNames = "path", description = "Path of the directory with the files to be processed", required = true, arity = OptionArity.EXACTLY_ONE) String path,
      @Option(longNames = "async", description = "Use async requests on HTTP level", arity = OptionArity.ZERO, defaultValue = "false") boolean async) {
    return """
        path %s
        async %s"""
        .formatted(path, async);
  }
}

I don't really understand when an option need to be named and when it doesn't. I have the following examples:

named argument

java .. experiment --path ABC
 < path ABC
 < async false

this works as expected

unnamed argument

java .. experiment ABC
 < path ABC
 < async false

This also works, but I wonder how spring-shell thinks that the unnamed argument is exactly path (especially, if there are multiple supported arguments)

unnamed argument with extra boolean option

java .. experiment --async ABC
 < Too many arguments for option 'async', requires at most '0'
 < Illegal option value 'ABC', reason 'Failed to convert from type [java.lang.String] to type [boolean] for value [ABC]'
 < Missing mandatory option '--path', Path of the directory with the files to be processed

As --async has arity=OptionArity.ZERO how comes that the following argument is interpreted as boolean?

named argument with extra boolean option

consequently, here I expect a cannot "convert --path to boolean" error, but this one works. Why?:

java .. experiment --async --path ABC
 < path ABC
 < async true

From the --async option aspect, this is the same as the previous call. Why does this work and no extra boolean is expected, but example 3 failed?

summary

I have lots of experience with Apache Commons CLI, getopt for C and getopts for bash. All of them seem to work in the same way and clear from the user point of view. But spring-shell looks different and inconsequent to me. I would use Apache CLI, but it seems wrong because it doesn't integrate nicely in a spring boot project.

Upvotes: 0

Views: 46

Answers (0)

Related Questions