From 20415104e2a3e145f70cdeaa3e3a9585fb026f00 Mon Sep 17 00:00:00 2001 From: morganamilo Date: Fri, 24 Jul 2020 22:39:44 +0100 Subject: [PATCH] Add support for lower/upper in rename_all Some programs do not use anything to seperate word boundaries. For example a struct make contain the field `build_dir` while the flag is `--builddir`. --- examples/rename_all.rs | 4 ++++ src/lib.rs | 4 ++-- structopt-derive/src/attrs.rs | 8 ++++++++ tests/argument_naming.rs | 28 ++++++++++++++++++++++++++++ 4 files changed, 42 insertions(+), 2 deletions(-) diff --git a/examples/rename_all.rs b/examples/rename_all.rs index 35f3c4f7..c7c3538a 100644 --- a/examples/rename_all.rs +++ b/examples/rename_all.rs @@ -17,6 +17,10 @@ //! - **Snake Case**: Keep all letters lowercase and indicate word boundaries //! with underscores. //! - **Verbatim**: Use the original attribute name defined in the code. +//! +//! - **Lower Case**: Keep all letters lowercase and remove word boundaries. +//! +//! - **Upper Case**: Keep all letters upperrcase and remove word boundaries. use structopt::StructOpt; diff --git a/src/lib.rs b/src/lib.rs index b45a2fe9..1da90482 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -280,7 +280,7 @@ //! Usable only on field-level. //! //! - [`rename_all`](#specifying-argument-types): -//! [`rename_all = "kebab"/"snake"/"screaming-snake"/"camel"/"pascal"/"verbatim"]` +//! [`rename_all = "kebab"/"snake"/"screaming-snake"/"camel"/"pascal"/"verbatim"/"lower"/"upper"]` //! //! Usable both on top level and field level. //! @@ -309,7 +309,7 @@ //! Usable only on field-level. //! //! - [`rename_all_env`](##auto-deriving-environment-variables): -//! [`rename_all_env = "kebab"/"snake"/"screaming-snake"/"camel"/"pascal"/"verbatim"]` +//! [`rename_all_env = "kebab"/"snake"/"screaming-snake"/"camel"/"pascal"/"verbatim"/"lower"/"upper"]` //! //! Usable both on top level and field level. //! diff --git a/structopt-derive/src/attrs.rs b/structopt-derive/src/attrs.rs index d75b50ca..b2125c03 100644 --- a/structopt-derive/src/attrs.rs +++ b/structopt-derive/src/attrs.rs @@ -65,6 +65,10 @@ pub enum CasingStyle { Snake, /// Use the original attribute name defined in the code. Verbatim, + /// Keep all letters lowercase and remove word boundaries. + Lower, + /// Keep all letters uppercase and remove word boundaries. + Upper, } #[derive(Clone)] @@ -188,6 +192,8 @@ impl CasingStyle { "screamingsnake" | "screamingsnakecase" => cs(ScreamingSnake), "snake" | "snakecase" => cs(Snake), "verbatim" | "verbatimcase" => cs(Verbatim), + "lower" | "lowercase" => cs(Lower), + "upper" | "uppercase" => cs(Upper), s => abort!(name, "unsupported casing: `{}`", s), } } @@ -208,6 +214,8 @@ impl Name { ScreamingSnake => s.to_shouty_snake_case(), Snake => s.to_snake_case(), Verbatim => s, + Lower => s.to_lowercase().replace("_", ""), + Upper => s.to_uppercase().replace("_", ""), }; quote_spanned!(ident.span()=> #s) } diff --git a/tests/argument_naming.rs b/tests/argument_naming.rs index e7fe3d55..88b549db 100644 --- a/tests/argument_naming.rs +++ b/tests/argument_naming.rs @@ -309,3 +309,31 @@ fn test_rename_all_is_propagation_can_be_overridden() { Opt::from_clap(&Opt::clap().get_matches_from(&["test", "SECOND_VARIANT", "--foo-option"])) ); } + +#[test] +fn test_lower_is_renamed() { + #[derive(StructOpt, Debug, PartialEq)] + struct Opt { + #[structopt(rename_all = "lower", long)] + foo_option: bool, + } + + assert_eq!( + Opt { foo_option: true }, + Opt::from_clap(&Opt::clap().get_matches_from(&["test", "--foooption"])) + ); +} + +#[test] +fn test_upper_is_renamed() { + #[derive(StructOpt, Debug, PartialEq)] + struct Opt { + #[structopt(rename_all = "upper", long)] + foo_option: bool, + } + + assert_eq!( + Opt { foo_option: true }, + Opt::from_clap(&Opt::clap().get_matches_from(&["test", "--FOOOPTION"])) + ); +}