bpaf
bpaf copied to clipboard
A way to prevent parsing of options after positionals
Perhaps related to #302, I'd like to be able to prevent parsing of options after positionals.
Given:
Usage: krun [--net=NET_MODE] [--passt-socket=PATH] COMMAND [COMMAND_ARGS]...
Available positional items:
COMMAND the command you want to execute in the vm
COMMAND_ARGS arguments of COMMAND
Available options:
--net=NET_MODE Set network mode NET_MODE can be either TSI (default) or PASST
[default: TSI]
--passt-socket=PATH Instead of starting passt, connect to passt socket at PATH
-h, --help Prints help information
If I do:
krun --net=PASST box64 --help
It should not be parsed as the --help option.
Sure, it's possible to just add -- but that's not always user-friendly.
So I can better understand the problem - what's the motivation for that?
As illustrated above, it's to pass all COMMAND_ARGS to COMMAND. So basically like any, but without this "problem":
“before” in the previous line means in the parser definition, not on the user input, here
--turbogets consumed byturboparser even the argument goes
https://docs.rs/bpaf/latest/bpaf/fn.any.html#use-any-to-capture-the-remaining-arguments
As illustrated above, it's to pass all
COMMAND_ARGStoCOMMAND.
I see. That's a bit tricky, my usual approach is to have different flags between inner and outer commands. To apply the restriction you want parser needs to run on arguments in order they are given on a command line, at the moment it runs in order they are specified in your parser. I need to think about an efficient way to allow this, might take some time.
my usual approach is to have different flags between inner and outer commands
COMMAND in this case is just any external program. So we don't know / don't care what the arguments are.
I have identified another (perhaps related) issue with any. I can't seem to get it to behave similarly like positional, while still consuming anything that comes after it.
To illustrate:
Given (the same program as before, but updated):
$ krun --help
Usage: krun [-e=ENV]... [--net=NET_MODE] [--passt-socket=PATH] COMMAND [COMMAND_ARGS]...
Available positional items:
COMMAND the command you want to execute in the vm
COMMAND_ARGS arguments of COMMAND
Available options:
-e, --env=ENV Set environment variable to be passed to the microVM
ENV should be in KEY=VALUE format, or KEY on its own to inherit the
current value from the local environment
--net=NET_MODE Set network mode NET_MODE can be either TSI (default) or PASST
[default: TSI]
--passt-socket=PATH Instead of starting passt, connect to passt socket at PATH
-h, --help Prints help information
If I do:
$ krun --net=PASST --net=PASST -- box64 --version
The second unconsumed --net=PASST ends up being consumed by any (COMMAND_ARGS). There should be a way to consume anything only from the current position, i.e. after COMMAND.
The code is here for your reference: https://github.com/teohhanhui/krun/blob/283a1f716f8c2078e9fbe6a4f2174bcba38b559e/crates/krun/src/cli_options.rs
I got some ideas how to implement it and for now I'm done messing with cargo-show-asm. I'll try to make something that can solve your problem soon-ish.
I pushed a right-adj branch that implements start_adjacent() method on parser trait. The idea is that the whole annotated block must be either directly adjacent to the beginning or to fully parsed block, so if you make it so xxx parses --net=PASST, but not box64 - parser like listed above will parse krun --net=PASST box64 --help by capturing "PASST" into xxx and ["box64", "--help"] into tail. At least for as long as xxx succeeds.
let option_parsers = xxx.start_adjacent();
let tail = any::<OsString, _, _>("TAIL", Some).many();
let parser = construct!(option_parsers, tail)
I'm planning to release a new version with it in a few days after covering some of other remaining issues.
This is addressing the original issue, right? But what about the other issue I found? :see_no_evil:
I'm looking into fixing it as well.
On Tue, Jul 2, 2024, 16:33 Teoh Han Hui @.***> wrote:
This is addressing the original issue, right? But what about the other issue I found? 🙈
— Reply to this email directly, view it on GitHub https://github.com/pacak/bpaf/issues/359#issuecomment-2204362718, or unsubscribe https://github.com/notifications/unsubscribe-auth/AAAQFI3PKKCKNBE72SYLC7TZKMFDNAVCNFSM6AAAAABG4OC75KVHI2DSMVQWIX3LMV43OSLTON2WKQ3PNVWWK3TUHMZDEMBUGM3DENZRHA . You are receiving this because you commented.Message ID: @.***>