I have the following type:
#[derive(clap::ValueEnum, Clone, Debug)]
pub enum Processor {
DefaultProcessor,
SecondaryProcessor,
}
I have a FromStr impl for this struct as well (not shown because it's very simple).
I am currently using this in a struct like this:
#[derive(Parser)]
pub struct RunLocalTestnet {
/// Processors to run.
#[clap(long)]
processors: Vec<Processor>,
}
So far so good, this works great. What I'm trying to do now is add a default value for this vector, for example:
#[clap(long, default_value_t = vec![Processor::DefaultProcessor])]
processors: Vec<Processor>,
Unfortunately when I do this I get the following error:
error[E0277]: `Vec<processor::processors::Processor>` doesn't implement `std::fmt::Display`
--> crates/aptos/src/node/local_testnet.rs:103:18
|
103 | #[clap(long, default_value_t = vec![Processor::DefaultProcessor])]
| ^^^^^^^^^^^^^^^ `Vec<processor::processors::Processor>` cannot be formatted with the default formatter
|
= help: the trait `std::fmt::Display` is not implemented for `Vec<processor::processors::Processor>`
= note: in format strings you may be able to use `{:?}` (or {:#?} for pretty-print) instead
= note: required for `Vec<processor::processors::Processor>` to implement `ToString`
Is there a way to make this work with Clap 4 (specifically 4.3.9) out of the box? I feel like it shouldn't be necessary to make Processor
impl Display
because it works up until I set the default value.
I believe you want default_values_t
(note the s
). default_value_t
requires the type to implement Display
or ValueEnum
which of course Vec<T>
does not. But default_values_t
requires the type to be a Vec<T>
where only T
has to implement Display
or ValueEnum
, which is exactly what you have.
Docs page: https://docs.rs/clap/4.3.9/clap/_derive/index.html
default_value = <str>
: Arg::default_value
and Arg::required(false)
default_value_t [= <expr>]
: Arg::default_value
and Arg::required(false)
std::fmt::Display
that roundtrips correctly with the Arg::value_parser
or #[arg(value_enum)]
<expr>
, relies on Default::default()
default_values_t = <expr>
: Arg::default_values
and Arg::required(false)
Vec<T>
and T
to implement std::fmt::Display
or #[arg(value_enum)]
<expr>
must implement IntoIterator<T>