I want one argument to imply another, though they don't take explicit values. --simple-anime
or --complex-anime
should imply --anime
. The API that should work is default_value_ifs
, saying that if either of the former is present, --anime
will also be true. The problem is that that option turns on takes_value
, and if I turn that off, the implication doesn't happen.
Simple example: --dog
implies --mammal
. Neither one should require a value--it is true if the argument is present.
use clap::Parser;
fn main() {
let args = Args::parse_from(["prog-name", "--dog"]);
assert_eq!(args.dog, true);
assert_eq!(args.mammal, true);
dbg!(&args);
let args = Args::try_parse_from(["prog-name", "--mammal"]);
dbg!(&args);
assert!(matches!(args, Ok(_)));
}
#[derive(Parser, Debug)]
#[clap()]
struct Args {
//#[clap(long, default_value_if("dog", None, Some("true")), takes_value(false))]
#[clap(long, default_value_if("dog", None, Some("true")))]
mammal: bool,
#[clap(long)]
dog: bool,
}
Try it in rust playground: https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=4855a88381f65cef8d07f7eab4d41e78
Instead of takes_value(false)
use min_values(0)
(playground):
#[clap(long, default_value_if("dog", None, Some("true")), min_values(0))]
mammal: bool,
It looks like the default value implementation uses the same code as the values, so if you disable one you disable the other.