dce-macro 1.8.0

The macros for the dce-router lib
Documentation
use proc_macro2::{Span, TokenStream};
use syn::{Error, Expr, ExprLit, Lit, LitInt, LitStr, Token, parse_quote};
use syn::parse::{Parse, ParseStream};
use syn::punctuated::Punctuated;

pub struct DceError {
    code: Expr,
    formatter: LitStr,
    args: Punctuated<Expr, Token![,]>
}

impl DceError {
    pub fn gen_func(self, public: bool) -> TokenStream {
        let DceError{code, formatter, args} = self;
        parse_quote!(dce_util::result::DceError::msg(#public, #code, format!(#formatter, #args)))
    }
}

impl Parse for DceError {
    fn parse(input: ParseStream) -> syn::Result<Self> {
        let (code, formatter) = match input.parse() {
            Ok(expr @ (Expr::Path(_) | Expr::Lit(ExprLit { lit: Lit::Int(_), .. }))) if input.parse::<Token![,]>().is_ok() && ! input.is_empty() => (
                expr,
                if let Ok(Expr::Lit(ExprLit { lit: Lit::Str(formatter), .. })) = input.parse() { formatter } else { unreachable!() }
            ),
            Ok(Expr::Lit(ExprLit { lit: Lit::Str(formatter), .. })) => (
                Expr::Lit(ExprLit{ attrs: vec![], lit: Lit::Int(LitInt::new("0", Span::call_site())) }),
                formatter
            ),
            _ => panic!("{}", Error::new(Span::call_site(), "Must special a valid message")),
        };
        let _ = input.parse::<Token![,]>();
        Ok(DceError{ code, formatter, args: Punctuated::parse_terminated(input)? })
    }
}