Support `allow_hyphen_values` in native completions
Please complete the following tasks
- [X] I have searched the discussions
- [X] I have searched the open and rejected issues
Clap Version
master
Describe your use case
use clap::{CommandFactory, Parser};
use clap_complete::dynamic::shells::CompleteCommand;
#[derive(Parser, Debug)]
#[clap(name = "dynamic", about = "A dynamic command line tool")]
struct Cli {
/// The subcommand to run complete
#[command(subcommand)]
complete: Option<CompleteCommand>,
/// Output format
#[clap(short = 'F', long, value_parser = ["--json", "--yaml", "--toml"], allow_hyphen_values = true)]
format: Option<String>,
#[clap(long)]
json: Option<String>,
}
fn main() {
let cli = Cli::parse();
if let Some(completions) = cli.complete {
completions.complete(&mut Cli::command());
}
// normal logic continues...
}
For the command line:
dynamic --format --json --js[TAB]
There is no completion generated. it should be:
dynamic --format --json --json
This seems to be a very specific use case, but it shows that there is an error in parsing during dynamic completion when the allow_hyphen_values setting is enabled, or that allow_hyphen_values is not being considered.
Describe the solution you'd like
https://github.com/clap-rs/clap/blob/5efa52ad4501393d50e236d10a979313a61d4929/clap_complete/src/dynamic/completer.rs#L76 https://github.com/clap-rs/clap/blob/5efa52ad4501393d50e236d10a979313a61d4929/clap_complete/src/dynamic/completer.rs#L79 https://github.com/clap-rs/clap/blob/5efa52ad4501393d50e236d10a979313a61d4929/clap_complete/src/dynamic/completer.rs#L112 do something more in these branches
Alternatives, if applicable
No response
Additional Context
There are also user cases related to the mistaken parsing.
Case 1
use clap::{CommandFactory, Parser};
use clap_complete::dynamic::shells::CompleteCommand;
#[derive(Parser, Debug)]
#[clap(name = "dynamic", about = "A dynamic command line tool")]
struct Cli {
/// The subcommand to run complete
#[command(subcommand)]
complete: Option<CompleteCommand>,
/// Output format
#[clap(short = 'F', long, value_parser = ["json", "yaml", "toml"], allow_hyphen_values = true)]
format: Option<String>,
#[clap(value_parser = ["--pos_a"], index = 1)]
positional_a: Option<String>,
#[clap(value_parser = ["pos_b"], index = 2)]
positional_b: Option<String>,
}
fn main() {
let cli = Cli::parse();
if let Some(completions) = cli.complete {
completions.complete(&mut Cli::command());
}
// normal logic continues...
}
For the command line
dynamic --format json --pos_a [TAB]
completions are:
--format --help --pos_a -F -h help
it should be:
pos_b --format --help -F -h help
Case 2
use clap::{CommandFactory, Parser};
use clap_complete::dynamic::shells::CompleteCommand;
#[derive(Parser, Debug)]
#[clap(name = "dynamic", about = "A dynamic command line tool")]
struct Cli {
/// The subcommand to run complete
#[command(subcommand)]
complete: Option<CompleteCommand>,
/// Output format
#[clap(short = 'F', long, value_parser = ["json", "yaml", "toml"], allow_hyphen_values = true)]
format: Option<String>,
#[clap(value_parser = ["-a"], index = 1)]
positional_a: Option<String>,
#[clap(value_parser = ["pos_b"], index = 2)]
positional_b: Option<String>,
}
fn main() {
let cli = Cli::parse();
if let Some(completions) = cli.complete {
completions.complete(&mut Cli::command());
}
// normal logic continues...
}
For the command line
dynamic --format json -a [TAB]
completions are:
--format --help -F -a -h help
it should be:
pos_b --format --help -F -h help
There is a related case https://github.com/clap-rs/clap/pull/5602#discussion_r1705107817.