Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

picocli does not seem to support - as a positional parameter #613

Closed
helpermethod opened this issue Jan 22, 2019 · 6 comments
Closed

picocli does not seem to support - as a positional parameter #613

helpermethod opened this issue Jan 22, 2019 · 6 comments
Labels
theme: parser An issue or change related to the parser type: enhancement ✨
Milestone

Comments

@helpermethod
Copy link

helpermethod commented Jan 22, 2019

Hi,

I'm preparing some demo project for picocli and stumbled over some interesting, currently unsupported case.

Some shell commands, like cat accept - as a positional parameter

cat -

which means cat will read it's input from STDIN instead of a file.

But it seems picocli currently doesn't support such a case?

When I call

@Command(name = "mst-cli", mixinStandardHelpOptions = true)
public class Cli implements Runnable {
    @Parameters(index = "0")
    private String json;
    @Parameters(index = "1")
    private String template;
    // more code
}

with the following parameters

- ~/hello.mustache

picocli complains that the second parameter isn't set :/.

But

~/data.json ~/hello.mustache

works.

@helpermethod helpermethod changed the title PicoCli does not seem to support - as a positional parameter picocli does not seem to support - as a positional parameter Jan 22, 2019
@remkop
Copy link
Owner

remkop commented Jan 22, 2019

Is there a stack trace or more detailed error message?

@remkop
Copy link
Owner

remkop commented Jan 22, 2019

I agree that the single dash character - is a common argument like you describe and it should be possible to have a positional parameter in picocli take this value. I’ll look into it when I get to my PC.

@remkop
Copy link
Owner

remkop commented Jan 22, 2019

I was able to reproduce the problem with this test:

@Test
public void testSingleDashPositionalParam() {
    @Command(name = "dashtest", mixinStandardHelpOptions = true)
    class App {
        @Parameters(index = "0")
        private String json;
        @Parameters(index = "1")
        private String template;
    }
    System.setProperty("picocli.trace", "DEBUG");
    App app = new App();
    CommandLine commandLine = new CommandLine(app);
    
    commandLine.parseArgs("-", "~/hello.mustache");
    assertEquals("-", app.json);
    assertEquals("~/hello.mustache", app.template);
}

I see the following DEBUG output:

[picocli DEBUG] Processing argument '-'. Remainder=[~/hello.mustache]
[picocli DEBUG] '-' cannot be separated into <option>=<option-parameter>
[picocli DEBUG] Could not find option '-', deciding whether to treat as unmatched option or positional parameter...
[picocli DEBUG] - resembles an option: 4 matching prefix chars out of 4 option names
[picocli DEBUG] Processing argument '~/hello.mustache'. Remainder=[]
[picocli DEBUG] '~/hello.mustache' cannot be separated into <option>=<option-parameter>
[picocli DEBUG] Could not find option '~/hello.mustache', deciding whether to treat as unmatched option or positional parameter...
[picocli DEBUG] ~/hello.mustache doesn't resemble an option: 0 matching prefix chars out of 4 option names
[picocli DEBUG] No option named '~/hello.mustache' found. Processing remainder as positional parameters
[picocli DEBUG] Processing next arg as a positional parameter at index=0. Remainder=[~/hello.mustache]
[picocli DEBUG] Position 0 is in index range 0. Trying to assign args to field String picocli.CommandLineTest$95App.json, arity=1
[picocli INFO] Setting field String picocli.CommandLineTest$95App.json to '~/hello.mustache' (was 'null') for args[0] at position 0
[picocli DEBUG] Consumed 1 arguments and 0 interactive values, moving position to index 1.

picocli.CommandLine$MissingParameterException: Missing required parameter: <template>

So the problem is that the single dash resembles an option in picocli's heuristics for unmatched arguments.

The workaround is to set

    commandLine.setUnmatchedOptionsArePositionalParams(true);

This will make parse the input as expected. Maybe the heuristic should be improved.

@remkop remkop added this to the 3.9.3 milestone Jan 22, 2019
@remkop remkop closed this as completed in b644a65 Jan 22, 2019
@remkop
Copy link
Owner

remkop commented Jan 22, 2019

Fixed in master.
Improved the heuristics for unmatched options: single-character arguments that don't exactly match options (like -) are now always considered positional parameters.

Please verify.

@remkop
Copy link
Owner

remkop commented Feb 1, 2019

Picocli 3.9.3 has been released. This includes a fix for this issue.

Enjoy!

@helpermethod
Copy link
Author

Thank you very much. Was very low on time the last few weeks so couldn't test the change :/.

@remkop remkop added the theme: parser An issue or change related to the parser label Apr 2, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
theme: parser An issue or change related to the parser type: enhancement ✨
Projects
None yet
Development

No branches or pull requests

2 participants