picocli icon indicating copy to clipboard operation
picocli copied to clipboard

`ArgGroup has no options or positional parameters, and no subgroups` since 4.7.7

Open snazy opened this issue 7 months ago • 3 comments

The upgrade to picocli 4.7.7 seems to cause a bunch of compiler errors in the picocli apt. 4.7.6 works fine.

The errors happen at all @ArgGroup annotated fields, for example this one or this one.

Example error in CI

Example picocli apt error stack trace:

error: FATAL ERROR: picocli.CommandLine$InitializationException: ArgGroup has no options or positional parameters, and no subgroups: AnnotatedElementHolder(FIELD jdbc in org.projectnessie.gc.tool.cli.commands.JdbcCreateSchema) in null
        at picocli.CommandLine$Model$ArgGroupSpec.<init>(CommandLine.java:10430)
        at picocli.CommandLine$Model$ArgGroupSpec$Builder.build(CommandLine.java:10928)
        at picocli.codegen.annotation.processing.AbstractCommandSpecProcessor$Context.connectArgGroups(AbstractCommandSpecProcessor.java:1043)
        at picocli.codegen.annotation.processing.AbstractCommandSpecProcessor$Context.connectModel(AbstractCommandSpecProcessor.java:907)
        at picocli.codegen.annotation.processing.AbstractCommandSpecProcessor$Context.access$000(AbstractCommandSpecProcessor.java:855)
        at picocli.codegen.annotation.processing.AbstractCommandSpecProcessor.tryProcess(AbstractCommandSpecProcessor.java:209)
        at picocli.codegen.annotation.processing.AbstractCommandSpecProcessor.process(AbstractCommandSpecProcessor.java:168)
        at org.gradle.api.internal.tasks.compile.processing.DelegatingProcessor.process(DelegatingProcessor.java:62)
...

snazy avatar Apr 24 '25 11:04 snazy

We are also affected by this. I've spent some time debugging.

Here's a simple repro:

@Command(name = "top", subcommands = {Main.Edit.class, Main.Update.class})
public class Main implements Callable<Integer> {

    public class UsernameAndPassword {
        @CommandLine.Option(names = "--user", required = false)
        String username;
        @CommandLine.Option(names = "--pwd", required = false)
        String password;
    }

    @Command(name = "edit")
    static class Update {
        @CommandLine.ArgGroup
        UsernameAndPassword usernamePassword;
    }

    @Command(name = "update")
    static class Edit {
        @CommandLine.ArgGroup
        UsernameAndPassword usernamePassword;
    }

which gives:

error: FATAL ERROR: picocli.CommandLine$InitializationException: ArgGroup has no options or positional parameters, and no subgroups: AnnotatedElementHolder(FIELD usernamePassword in com.company.Main.Update) in null
        at picocli.CommandLine$Model$ArgGroupSpec.<init>(CommandLine.java:10431)
        at picocli.CommandLine$Model$ArgGroupSpec$Builder.build(CommandLine.java:10929)

I think it fails when the same class is reused as ArgGroup in more than 1 class. I am not fully sure, but I suspect this might have something to do with it:

  • the code in the ArgGroupSpec constructor assumes the builder is mutable and used for only one arg group
  • specifically statements like arg.group = this; might be executed against the same ArgGroup builder for UsernameAndPassword in two different contexts: one for Edit, one for Update command. Effectively "competing" with each other.

greg-at-moderne avatar Apr 25 '25 09:04 greg-at-moderne

I'm also hitting this, in https://github.com/enola-dev/enola/pull/1324, which fails here with the same:

ERROR: /home/runner/work/enola/enola/java/dev/enola/cli/BUILD:35:13: Building java/dev/enola/cli/liblib-class.jar (31 source files) and running annotation processors (NativeImageConfigGeneratorProcessor) failed: (Exit 1): java failed: error executing Javac command (from target //java/dev/enola/cli:lib) external/rules_java++toolchains+remotejdk21_linux/bin/java '--add-exports=jdk.compiler/com.sun.tools.javac.api=ALL-UNNAMED' '--add-exports=jdk.compiler/com.sun.tools.javac.main=ALL-UNNAMED' ... (remaining 19 arguments skipped)
error: FATAL ERROR: picocli.CommandLine$InitializationException: ArgGroup has no options or positional parameters, and no subgroups: AnnotatedElementHolder(FIELD output in dev.enola.cli.CanonicalizeCommand) in null
  	at picocli.CommandLine$Model$ArgGroupSpec.<init>(CommandLine.java:10430)
  	at picocli.CommandLine$Model$ArgGroupSpec$Builder.build(CommandLine.java:10928)
  	at picocli.codegen.annotation.processing.AbstractCommandSpecProcessor$Context.connectArgGroups(AbstractCommandSpecProcessor.java:1043)
  	at picocli.codegen.annotation.processing.AbstractCommandSpecProcessor$Context.connectModel(AbstractCommandSpecProcessor.java:907)
...

it comes from here for this and this ArgGroup.

vorburger avatar Apr 30 '25 16:04 vorburger

Seen also in

https://github.com/jonesbusy/oras-java-cli/pull/16 https://github.com/jenkins-infra/plugin-modernizer-tool/pull/960

jonesbusy avatar May 03 '25 07:05 jonesbusy