rialo_sol_derive_serde/
lib.rs1#[allow(unused_extern_crates)]
9extern crate proc_macro;
10
11#[cfg(feature = "lazy-account")]
12mod lazy;
13
14use proc_macro::TokenStream;
15use proc_macro2::{Span, TokenStream as TokenStream2};
16use proc_macro_crate::FoundCrate;
17use quote::quote;
18use syn::Ident;
19
20fn gen_borsh_serialize(input: TokenStream) -> TokenStream2 {
21 let input = TokenStream2::from(input);
22 let attrs = helper_attrs("BorshSerialize");
23 quote! {
24 #attrs
25 #input
26 }
27}
28
29#[proc_macro_derive(SolSerialize)]
30pub fn sol_serialize(input: TokenStream) -> TokenStream {
31 #[cfg(not(feature = "idl-build"))]
32 let ret = gen_borsh_serialize(input);
33 #[cfg(feature = "idl-build")]
34 let ret = gen_borsh_serialize(input.clone());
35
36 #[cfg(feature = "idl-build")]
37 {
38 use quote::quote;
39 use rialo_sol_syn::idl::*;
40 use syn::Item;
41
42 let idl_build_impl = match syn::parse(input).unwrap() {
43 Item::Struct(item) => impl_idl_build_struct(&item),
44 Item::Enum(item) => impl_idl_build_enum(&item),
45 Item::Union(item) => impl_idl_build_union(&item),
46 _ => unreachable!(),
48 };
49
50 return TokenStream::from(quote! {
51 #ret
52 #idl_build_impl
53 });
54 };
55
56 #[allow(unreachable_code)]
57 TokenStream::from(ret)
58}
59
60fn gen_borsh_deserialize(input: TokenStream) -> TokenStream2 {
61 let input = TokenStream2::from(input);
62 let attrs = helper_attrs("BorshDeserialize");
63 quote! {
64 #attrs
65 #input
66 }
67}
68
69#[proc_macro_derive(SolDeserialize)]
70pub fn sol_deserialize(input: TokenStream) -> TokenStream {
71 #[cfg(feature = "lazy-account")]
72 {
73 let deser = gen_borsh_deserialize(input.clone());
74 let lazy = lazy::gen_lazy(input).unwrap_or_else(|e| e.to_compile_error());
75 quote::quote! {
76 #deser
77 #lazy
78 }
79 .into()
80 }
81 #[cfg(not(feature = "lazy-account"))]
82 gen_borsh_deserialize(input).into()
83}
84
85fn helper_attrs(mac: &str) -> TokenStream2 {
86 let mac_path = Ident::new(mac, Span::call_site());
94 let sol_lang = proc_macro_crate::crate_name("rialo-sol-lang")
95 .expect("`rialo-sol-derive-serde` must be used via `rialo-sol-lang`");
96
97 let sol_lang_path = Ident::new(
98 match &sol_lang {
99 FoundCrate::Itself => "crate",
100 FoundCrate::Name(cr) => cr.as_str(),
101 },
102 Span::call_site(),
103 );
104 let borsh_path = quote! { #sol_lang_path::prelude::borsh };
105 let borsh_path_str = borsh_path.to_string();
106
107 quote! {
108 #[derive(#borsh_path::#mac_path)]
109 #[borsh(crate = #borsh_path_str)]
111 #[#sol_lang_path::__erase]
112 }
113}
114
115#[doc(hidden)]
117#[proc_macro_attribute]
118pub fn __erase(_: TokenStream, _: TokenStream) -> TokenStream {
119 TokenStream::new()
120}
121
122#[cfg(feature = "lazy-account")]
123#[proc_macro_derive(Lazy)]
124pub fn lazy_derive(input: TokenStream) -> TokenStream {
125 lazy::gen_lazy(input)
126 .unwrap_or_else(|e| e.to_compile_error())
127 .into()
128}