aboutsummaryrefslogtreecommitdiff
path: root/jsonrpc/jsonrpc_macro
diff options
context:
space:
mode:
authorhozan23 <hozan23@karyontech.net>2024-04-11 10:19:20 +0200
committerhozan23 <hozan23@karyontech.net>2024-05-19 13:51:30 +0200
commit0992071a7f1a36424bcfaf1fbc84541ea041df1a (patch)
tree961d73218af672797d49f899289bef295bc56493 /jsonrpc/jsonrpc_macro
parenta69917ecd8272a4946cfd12c75bf8f8c075b0e50 (diff)
add support for tokio & improve net crate api
Diffstat (limited to 'jsonrpc/jsonrpc_macro')
-rw-r--r--jsonrpc/jsonrpc_macro/Cargo.toml24
-rw-r--r--jsonrpc/jsonrpc_macro/src/lib.rs47
2 files changed, 71 insertions, 0 deletions
diff --git a/jsonrpc/jsonrpc_macro/Cargo.toml b/jsonrpc/jsonrpc_macro/Cargo.toml
new file mode 100644
index 0000000..17140c5
--- /dev/null
+++ b/jsonrpc/jsonrpc_macro/Cargo.toml
@@ -0,0 +1,24 @@
+[package]
+name = "karyon_jsonrpc_macro"
+version.workspace = true
+edition.workspace = true
+
+# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
+
+[lib]
+proc-macro = true
+
+[features]
+default = ["smol"]
+smol = ["karyon_jsonrpc_internal/smol"]
+tokio = ["karyon_jsonrpc_internal/tokio"]
+
+[dependencies]
+karyon_jsonrpc_internal = { path = "../jsonrpc_internal", default-features = false }
+
+proc-macro2 = "1.0"
+quote = "1.0"
+syn = { version = "1.0", features = ["full"] }
+
+serde_json = "1.0.114"
+
diff --git a/jsonrpc/jsonrpc_macro/src/lib.rs b/jsonrpc/jsonrpc_macro/src/lib.rs
new file mode 100644
index 0000000..f2015d4
--- /dev/null
+++ b/jsonrpc/jsonrpc_macro/src/lib.rs
@@ -0,0 +1,47 @@
+use proc_macro::TokenStream;
+use proc_macro2::{Ident, TokenStream as TokenStream2};
+use quote::quote;
+use syn::{parse_macro_input, spanned::Spanned, ImplItem, ItemImpl, Type};
+
+macro_rules! err {
+ ($($tt:tt)*) => {
+ return syn::Error::new($($tt)*).to_compile_error().into()
+ };
+}
+
+#[proc_macro_attribute]
+pub fn rpc_impl(_attr: TokenStream, item: TokenStream) -> TokenStream {
+ let mut methods: Vec<Ident> = vec![];
+
+ let item2 = item.clone();
+ let parsed_input = parse_macro_input!(item2 as ItemImpl);
+
+ let self_ty = match *parsed_input.self_ty {
+ Type::Path(p) => p,
+ _ => err!(
+ parsed_input.span(),
+ "implementing the trait `RPCService` on this type is unsupported"
+ ),
+ };
+
+ if parsed_input.items.is_empty() {
+ err!(self_ty.span(), "At least one method should be implemented");
+ }
+
+ for item in parsed_input.items {
+ match item {
+ ImplItem::Method(method) => {
+ methods.push(method.sig.ident);
+ }
+ _ => err!(item.span(), "unexpected item"),
+ }
+ }
+
+ let item2: TokenStream2 = item.into();
+ let quoted = quote! {
+ karyon_jsonrpc_internal::impl_rpc_service!(#self_ty, #(#methods),*);
+ #item2
+ };
+
+ quoted.into()
+}