picocli 中具有默认值的 arggroup

arggroup with default value in picocli

用Java代码编写cmd界面使用picocli v4.6.3

我的情况: ./cmd [-a -b [-c]]

用户输入a,b选项或得到默认值 示例:

@Command
public class CMD implements Runnable {

    @Parameters
    private String x;

    
    @ArgGroup(exclusive = false)
    private Group group;

    static class Group {
        @Option(names = "-a", required = true, defaultValue = "aa")
        public static String a;

        @Option(names = "-b", required = true, defaultValue = "bb")
        public static String b;

        @Option(names = "-c", required = false, defaultValue = "cc")
        public static String c;
    }

但它并没有如我所愿 我没有解决方案

原答案

picocli 用户手册在 assigning default values in argument groups 上有一个详细的部分。

应用程序需要执行以下两项操作:

  • @Option 注释和 @Option 注释字段的初始值中指定默认值。 (是的,这意味着一些重复。)
  • 手动实例化 @ArgGroup-注释字段

对于您的示例,这意味着:

@Command
public class CMD implements Runnable {

    @Parameters
    private String x;
    
    @ArgGroup(exclusive = false)
    private Group group = new Group();

    static class Group {
        @Option(names = "-a", required = true, defaultValue = "aa")
        public static String a = "aa";

        @Option(names = "-b", required = true, defaultValue = "bb")
        public static String b = "bb";

        @Option(names = "-c", required = false, defaultValue = "cc")
        public static String c = "cc";
    }

更新(答案 #2)

@kienbui 指出我错过了这些要求:

(...) if -a is specified, then -b becomes mandatory (user input becomes required), and similarly if -b is specified, then -a becomes mandatory. Otherwise, if neither -a nor -b is specified, none of the options are required and default values are assigned to the options that are not specified by the end user.

这可以通过为选项 -a-b 创建单独的内部 arg-group 并从选项声明中删除默认值,但使用默认值初始化它们来实现值。 例如:

@Command
static class CMD implements Runnable {

    @Parameters
    private String x;

    @ArgGroup(exclusive = false)
    private Group group = new Group();

    static class Group {
        @ArgGroup(exclusive = false)
        private InnerGroup inner = new InnerGroup("aa", "bb"); // default values

        @Option(names = "-c", required = false, defaultValue = "cc")
        public String c = "cc";
    }

    static class InnerGroup {
        // default constructor, used by picocli when
        // one or more options in this group are 
        // matched on the command line
        public InnerGroup() {}

        // this constructor assigns default values,
        // used only when *both* options are missing
        public InnerGroup(String a, String b) {
            this.a = a;
            this.b = b;
        }

        @Option(names = "-a", required = true)
        public String a;

        @Option(names = "-b", required = true)
        public String b;
    }

    @Override
    public void run() {
        System.out.printf("a=%s, b=%s, c=%s, x=%s%n", 
                group.inner.a, group.inner.b, group.c, x);
    }
}