//! Typed outgoing calls and statically registered imported interfaces. use crate::{Call, Result}; use serde_json::Value; use std::{future::IntoFuture, marker::PhantomData}; /// An imported provider document registered by `import!`. #[doc(hidden)] pub struct Import { /// The provider name. pub name: &'static str, /// Its complete OpenRPC document. pub document: &'static str, } inventory::collect!(Import); /// An outgoing call whose result decodes to a generated Rust type. #[must_use = "await the call to send it"] pub struct TypedCall { call: Call, result: PhantomData, } impl TypedCall { /// Wrap an untyped call without sending it yet. pub fn new(call: Call) -> Self { Self { call, result: PhantomData, } } /// Detach the child process from its caller. pub fn detach(mut self) -> Self { self.call = self.call.detach(); self } /// Receive progress notifications while the call runs. pub fn on_notify(mut self, f: impl FnMut(&str, Value) + 'static) -> Self { self.call = self.call.on_notify(f); self } } impl IntoFuture for TypedCall { type Output = Result; type IntoFuture = futures::future::LocalBoxFuture<'static, Result>; fn into_future(self) -> Self::IntoFuture { Box::pin(async move { Ok(serde_json::from_value(self.call.await?)?) }) } }