asmov_common_testing_macro/
lib.rs1use proc_macro;
2use proc_macro2;
3use quote::quote;
4use syn;
5
6#[proc_macro_attribute]
7pub fn tested(attr: proc_macro::TokenStream, item: proc_macro::TokenStream) -> proc_macro::TokenStream {
8 match parse_tested_macro(proc_macro2::TokenStream::from(attr), proc_macro2::TokenStream::from(item)) {
9 Ok(token_stream) => proc_macro::TokenStream::from(token_stream),
10 Err(err) => proc_macro::TokenStream::from(err.to_compile_error())
11 }
12}
13
14fn parse_tested_macro(_attr: proc_macro2::TokenStream, item: proc_macro2::TokenStream) -> syn::Result<proc_macro2::TokenStream> {
15 let item: syn::ItemFn = syn::parse2(item)?;
16
17 let test_attr = if let Some(_)= item.attrs.iter().find(|attr| attr.path().is_ident("test")) {
19 quote!{}
20 } else {
21 quote!{ #[test] }
22 };
23
24 let named_attr = if let Some(_)= item.attrs.iter().find(|attr| attr.path().is_ident("named")) {
26 quote!{}
27 } else {
28 quote!{ #[named] }
29 };
30
31 let output = quote! {
32 #named_attr
33 #test_attr
34 #item
35 };
36
37 Ok(output)
38}
39
40#[cfg(test)]
41mod tests {
42 use super::*;
43
44 #[test]
45 fn test_attr() {
46 let test_one_attr = quote::quote!{
47 #[tested]
48 };
49
50 let test_one_item = quote::quote!{
51 fn test_one() {}
52 };
53
54 parse_tested_macro(test_one_attr, test_one_item).unwrap();
55 }
56}