mirror of
https://github.com/clap-rs/clap
synced 2024-12-14 06:42:33 +00:00
refactor(derive): Only pass around what is needed
This commit is contained in:
parent
a86cb8a26c
commit
a47462123c
4 changed files with 41 additions and 33 deletions
|
@ -36,7 +36,8 @@ pub fn derive_args(input: &DeriveInput) -> TokenStream {
|
||||||
}) => {
|
}) => {
|
||||||
let name = Name::Derived(ident.clone());
|
let name = Name::Derived(ident.clone());
|
||||||
let item = Item::from_args_struct(input, name);
|
let item = Item::from_args_struct(input, name);
|
||||||
gen_for_struct(&item, ident, &input.generics, &fields.named)
|
let fields = &fields.named;
|
||||||
|
gen_for_struct(&item, ident, &input.generics, fields)
|
||||||
}
|
}
|
||||||
Data::Struct(DataStruct {
|
Data::Struct(DataStruct {
|
||||||
fields: Fields::Unit,
|
fields: Fields::Unit,
|
||||||
|
@ -44,12 +45,8 @@ pub fn derive_args(input: &DeriveInput) -> TokenStream {
|
||||||
}) => {
|
}) => {
|
||||||
let name = Name::Derived(ident.clone());
|
let name = Name::Derived(ident.clone());
|
||||||
let item = Item::from_args_struct(input, name);
|
let item = Item::from_args_struct(input, name);
|
||||||
gen_for_struct(
|
let fields = &Punctuated::<Field, Comma>::new();
|
||||||
&item,
|
gen_for_struct(&item, ident, &input.generics, fields)
|
||||||
ident,
|
|
||||||
&input.generics,
|
|
||||||
&Punctuated::<Field, Comma>::new(),
|
|
||||||
)
|
|
||||||
}
|
}
|
||||||
_ => abort_call_site!("`#[derive(Args)]` only supports non-tuple structs"),
|
_ => abort_call_site!("`#[derive(Args)]` only supports non-tuple structs"),
|
||||||
}
|
}
|
||||||
|
|
|
@ -16,9 +16,11 @@ use proc_macro2::TokenStream;
|
||||||
use proc_macro_error::abort_call_site;
|
use proc_macro_error::abort_call_site;
|
||||||
use quote::quote;
|
use quote::quote;
|
||||||
use syn::Ident;
|
use syn::Ident;
|
||||||
|
use syn::Token;
|
||||||
|
use syn::Variant;
|
||||||
use syn::{
|
use syn::{
|
||||||
self, punctuated::Punctuated, token::Comma, Data, DataEnum, DataStruct, DeriveInput, Field,
|
self, punctuated::Punctuated, token::Comma, Data, DataStruct, DeriveInput, Field, Fields,
|
||||||
Fields, Generics,
|
Generics,
|
||||||
};
|
};
|
||||||
|
|
||||||
use crate::derives::{args, into_app, subcommand};
|
use crate::derives::{args, into_app, subcommand};
|
||||||
|
@ -40,7 +42,8 @@ pub fn derive_parser(input: &DeriveInput) -> TokenStream {
|
||||||
.ok()
|
.ok()
|
||||||
.unwrap_or_default()));
|
.unwrap_or_default()));
|
||||||
let item = Item::from_args_struct(input, name);
|
let item = Item::from_args_struct(input, name);
|
||||||
gen_for_struct(&item, ident, &input.generics, &fields.named)
|
let fields = &fields.named;
|
||||||
|
gen_for_struct(&item, ident, &input.generics, fields)
|
||||||
}
|
}
|
||||||
Data::Struct(DataStruct {
|
Data::Struct(DataStruct {
|
||||||
fields: Fields::Unit,
|
fields: Fields::Unit,
|
||||||
|
@ -52,12 +55,8 @@ pub fn derive_parser(input: &DeriveInput) -> TokenStream {
|
||||||
.ok()
|
.ok()
|
||||||
.unwrap_or_default()));
|
.unwrap_or_default()));
|
||||||
let item = Item::from_args_struct(input, name);
|
let item = Item::from_args_struct(input, name);
|
||||||
gen_for_struct(
|
let fields = &Punctuated::<Field, Comma>::new();
|
||||||
&item,
|
gen_for_struct(&item, ident, &input.generics, fields)
|
||||||
ident,
|
|
||||||
&input.generics,
|
|
||||||
&Punctuated::<Field, Comma>::new(),
|
|
||||||
)
|
|
||||||
}
|
}
|
||||||
Data::Enum(ref e) => {
|
Data::Enum(ref e) => {
|
||||||
dummies::parser_enum(ident);
|
dummies::parser_enum(ident);
|
||||||
|
@ -66,7 +65,8 @@ pub fn derive_parser(input: &DeriveInput) -> TokenStream {
|
||||||
.ok()
|
.ok()
|
||||||
.unwrap_or_default()));
|
.unwrap_or_default()));
|
||||||
let item = Item::from_subcommand_enum(input, name);
|
let item = Item::from_subcommand_enum(input, name);
|
||||||
gen_for_enum(&item, ident, &input.generics, e)
|
let variants = &e.variants;
|
||||||
|
gen_for_enum(&item, ident, &input.generics, variants)
|
||||||
}
|
}
|
||||||
_ => abort_call_site!("`#[derive(Parser)]` only supports non-tuple structs and enums"),
|
_ => abort_call_site!("`#[derive(Parser)]` only supports non-tuple structs and enums"),
|
||||||
}
|
}
|
||||||
|
@ -91,11 +91,16 @@ fn gen_for_struct(
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn gen_for_enum(item: &Item, item_name: &Ident, generics: &Generics, e: &DataEnum) -> TokenStream {
|
fn gen_for_enum(
|
||||||
|
item: &Item,
|
||||||
|
item_name: &Ident,
|
||||||
|
generics: &Generics,
|
||||||
|
variants: &Punctuated<Variant, Token![,]>,
|
||||||
|
) -> TokenStream {
|
||||||
let (impl_generics, ty_generics, where_clause) = generics.split_for_impl();
|
let (impl_generics, ty_generics, where_clause) = generics.split_for_impl();
|
||||||
|
|
||||||
let into_app = into_app::gen_for_enum(item, item_name, generics);
|
let into_app = into_app::gen_for_enum(item, item_name, generics);
|
||||||
let subcommand = subcommand::gen_for_enum(item, item_name, generics, e);
|
let subcommand = subcommand::gen_for_enum(item, item_name, generics, variants);
|
||||||
|
|
||||||
quote! {
|
quote! {
|
||||||
impl #impl_generics clap::Parser for #item_name #ty_generics #where_clause {}
|
impl #impl_generics clap::Parser for #item_name #ty_generics #where_clause {}
|
||||||
|
|
|
@ -16,8 +16,8 @@ use proc_macro2::{Ident, Span, TokenStream};
|
||||||
use proc_macro_error::{abort, abort_call_site};
|
use proc_macro_error::{abort, abort_call_site};
|
||||||
use quote::{format_ident, quote, quote_spanned};
|
use quote::{format_ident, quote, quote_spanned};
|
||||||
use syn::{
|
use syn::{
|
||||||
punctuated::Punctuated, spanned::Spanned, Data, DataEnum, DeriveInput, FieldsUnnamed, Generics,
|
punctuated::Punctuated, spanned::Spanned, Data, DeriveInput, FieldsUnnamed, Generics, Token,
|
||||||
Token, Variant,
|
Variant,
|
||||||
};
|
};
|
||||||
|
|
||||||
use crate::derives::args;
|
use crate::derives::args;
|
||||||
|
@ -34,7 +34,8 @@ pub fn derive_subcommand(input: &DeriveInput) -> TokenStream {
|
||||||
Data::Enum(ref e) => {
|
Data::Enum(ref e) => {
|
||||||
let name = Name::Derived(ident.clone());
|
let name = Name::Derived(ident.clone());
|
||||||
let item = Item::from_subcommand_enum(input, name);
|
let item = Item::from_subcommand_enum(input, name);
|
||||||
gen_for_enum(&item, ident, &input.generics, e)
|
let variants = &e.variants;
|
||||||
|
gen_for_enum(&item, ident, &input.generics, variants)
|
||||||
}
|
}
|
||||||
_ => abort_call_site!("`#[derive(Subcommand)]` only supports enums"),
|
_ => abort_call_site!("`#[derive(Subcommand)]` only supports enums"),
|
||||||
}
|
}
|
||||||
|
@ -44,16 +45,16 @@ pub fn gen_for_enum(
|
||||||
item: &Item,
|
item: &Item,
|
||||||
item_name: &Ident,
|
item_name: &Ident,
|
||||||
generics: &Generics,
|
generics: &Generics,
|
||||||
e: &DataEnum,
|
variants: &Punctuated<Variant, Token![,]>,
|
||||||
) -> TokenStream {
|
) -> TokenStream {
|
||||||
let (impl_generics, ty_generics, where_clause) = generics.split_for_impl();
|
let (impl_generics, ty_generics, where_clause) = generics.split_for_impl();
|
||||||
|
|
||||||
let from_arg_matches = gen_from_arg_matches(&e.variants, item);
|
let from_arg_matches = gen_from_arg_matches(variants, item);
|
||||||
let update_from_arg_matches = gen_update_from_arg_matches(&e.variants, item);
|
let update_from_arg_matches = gen_update_from_arg_matches(variants, item);
|
||||||
|
|
||||||
let augmentation = gen_augment(&e.variants, item, false);
|
let augmentation = gen_augment(variants, item, false);
|
||||||
let augmentation_update = gen_augment(&e.variants, item, true);
|
let augmentation_update = gen_augment(variants, item, true);
|
||||||
let has_subcommand = gen_has_subcommand(&e.variants, item);
|
let has_subcommand = gen_has_subcommand(variants, item);
|
||||||
|
|
||||||
quote! {
|
quote! {
|
||||||
#[allow(dead_code, unreachable_code, unused_variables, unused_braces)]
|
#[allow(dead_code, unreachable_code, unused_variables, unused_braces)]
|
||||||
|
|
|
@ -13,8 +13,8 @@ use proc_macro_error::{abort, abort_call_site};
|
||||||
use quote::quote;
|
use quote::quote;
|
||||||
use quote::quote_spanned;
|
use quote::quote_spanned;
|
||||||
use syn::{
|
use syn::{
|
||||||
punctuated::Punctuated, spanned::Spanned, token::Comma, Data, DataEnum, DeriveInput, Fields,
|
punctuated::Punctuated, spanned::Spanned, token::Comma, Data, DeriveInput, Fields, Ident,
|
||||||
Ident, Variant,
|
Variant,
|
||||||
};
|
};
|
||||||
|
|
||||||
use crate::dummies;
|
use crate::dummies;
|
||||||
|
@ -29,14 +29,19 @@ pub fn derive_value_enum(input: &DeriveInput) -> TokenStream {
|
||||||
Data::Enum(ref e) => {
|
Data::Enum(ref e) => {
|
||||||
let name = Name::Derived(ident.clone());
|
let name = Name::Derived(ident.clone());
|
||||||
let item = Item::from_value_enum(input, name);
|
let item = Item::from_value_enum(input, name);
|
||||||
gen_for_enum(&item, ident, e)
|
let variants = &e.variants;
|
||||||
|
gen_for_enum(&item, ident, variants)
|
||||||
}
|
}
|
||||||
_ => abort_call_site!("`#[derive(ValueEnum)]` only supports enums"),
|
_ => abort_call_site!("`#[derive(ValueEnum)]` only supports enums"),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn gen_for_enum(item: &Item, item_name: &Ident, e: &DataEnum) -> TokenStream {
|
pub fn gen_for_enum(
|
||||||
let lits = lits(&e.variants, item);
|
item: &Item,
|
||||||
|
item_name: &Ident,
|
||||||
|
variants: &Punctuated<Variant, Comma>,
|
||||||
|
) -> TokenStream {
|
||||||
|
let lits = lits(variants, item);
|
||||||
let value_variants = gen_value_variants(&lits);
|
let value_variants = gen_value_variants(&lits);
|
||||||
let to_possible_value = gen_to_possible_value(&lits);
|
let to_possible_value = gen_to_possible_value(&lits);
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue