Skip to main content

child_of/
lib.rs

1#![no_implicit_prelude]
2#![forbid(absolute_paths_not_starting_with_crate)]
3
4extern crate std;
5extern crate syn;
6extern crate quote;
7extern crate proc_macro;
8
9use crate::std::*;
10use crate::std::convert::*;
11use crate::syn::*;
12use crate::quote::quote;
13use crate::proc_macro::*;
14
15#[proc_macro_attribute]
16pub fn child_of(attr: TokenStream, item: TokenStream) -> TokenStream {
17    let base_type = parse_macro_input!(attr as Type);
18    let item = parse_macro_input!(item as Item);
19    if let Item::Struct(mut struct_item) = item {
20        if let Fields::Named(fields) = &mut struct_item.fields {
21            let field: Field = parse_quote! { base: #base_type };
22            fields.named.insert(0, field);
23            quote!(#struct_item).into()
24        } else {
25            Error::new_spanned(struct_item, "#[child_of] can only be used on structs with named fields").to_compile_error().into()
26        }
27    } else {
28        Error::new_spanned(item, "#[child_of] can only be used on structs").to_compile_error().into()
29    }
30}