Skip to content
This repository has been archived by the owner on Jan 1, 2022. It is now read-only.

Compute argument possible values based on other arguments #157

Open
epage opened this issue Dec 6, 2021 · 6 comments
Open

Compute argument possible values based on other arguments #157

epage opened this issue Dec 6, 2021 · 6 comments
Milestone

Comments

@epage
Copy link
Owner

epage commented Dec 6, 2021

Issue by fbecart
Wednesday May 06, 2020 at 12:31 GMT
Originally opened as clap-rs/clap#1910


I would like to be able to compute the possible values of an argument dynamically, based on the values provided for some other argument(s).

Use case

I'm working on a CLI which has a goal similar to make.

$ make --help
Usage: make [options] [target] ...
Options:
  -f FILE, --file=FILE, --makefile=FILE
                              Read FILE as a makefile.

The file lists the available targets. Given a value of FILE, I am able to load a list of available target names. I would like to use that list as the possible values for target.

This would affect the validation of target. Ideally, this would also affect its autocompletion.

Currently, possible_values is expected to be provided as an array slice (&[&str]) as the App is being built.
https://github.com/clap-rs/clap/blob/9d03c8497ce17486e31b19fecbe5bec97ac82d09/src/build/arg/mod.rs#L1712
At that time, the value of FILE is not available yet.

Wanted solution

I would like instead to be able to provide a closure that would compute the possible values for my argument. This closure would take the values of the other app arguments as a parameter.

Workaround

It is already possible to obtain this behavior by parsing the arguments twice (the second time with refined validation):

fn get_app(allowed_target_names: Option<Vec<&str>>) -> App {
    let target_arg = Arg::with_name("target");

    let target_arg = if let Some(allowed_target_names) = allowed_target_names {
        target_arg.possible_values(&allowed_target_names)
    } else {
        target_arg
    };

    App::new("make")
        .arg(target_arg)
        [...]
}

fn main() {
    let arg_matches = get_app(None).get_matches();

    let config = Config::load(arg_matches.value_of("config_file"));
    let all_target_names = config.list_target_names();

    let app_args = get_app(Some(all_target_names)).get_matches();

    [...]
}

However, this workaround doubles the overhead of parsing arguments. Also, this solution does not cover the autocompletion part.

Related issues

@epage epage added this to the 3.1 milestone Dec 6, 2021
@epage
Copy link
Owner Author

epage commented Dec 6, 2021

Comment by pksunkara
Wednesday May 06, 2020 at 15:11 GMT


I think this can be achieved by the hooks proposal mentioned in #1471.

@epage
Copy link
Owner Author

epage commented Dec 6, 2021

Comment by fbecart
Thursday May 07, 2020 at 06:55 GMT


Thanks @pksunkara for looking into it. I see how clap-rs/clap#1471 is related, as it suggests to have a closure returning the default value of an argument.

This issue remains unique in the following ways:

  • It is about computing the possible values of an argument.
  • It requires access to the arguments that have already been provided.
  • It should influence auto-completion.
  • It is not related to prompting the user -- which is the primary motive for default value hooks.

@epage
Copy link
Owner Author

epage commented Dec 6, 2021

Comment by pksunkara
Thursday May 07, 2020 at 12:24 GMT


It is related because we can extend the hook proposal to allow defining possible values too. Prompts is a tangential issue.

Auto completion will probably be tied into the dynamic completion issue.

@epage
Copy link
Owner Author

epage commented Dec 6, 2021

Comment by fbecart
Friday May 08, 2020 at 20:27 GMT


To illustrate the issue, here's a link to the project I'm working on: https://github.com/fbecart/zinoma/blob/9d2ea034d566a92a7464a7ca58c0b75cb87d7072/src/main.rs#L32-L37

@epage
Copy link
Owner Author

epage commented Dec 6, 2021

Comment by kbknapp
Monday May 11, 2020 at 18:43 GMT


Also potentially related #1880

@epage
Copy link
Owner Author

epage commented Dec 6, 2021

Comment by fbecart
Wednesday Aug 05, 2020 at 17:19 GMT


Closely related to clap-rs/clap#1232, if not duplicate.

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

No branches or pull requests

1 participant